5 Author: Pekka Riikonen <priikone@silcnet.org>
7 Copyright (C) 2000 - 2005 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; version 2 of the License.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
21 #include "silcincludes.h"
23 #include "groups_internal.h"
25 /* Static functions */
26 static SilcSKEStatus silc_ske_create_rnd(SilcSKE ske, SilcMPInt *n,
29 static SilcSKEStatus silc_ske_make_hash(SilcSKE ske,
30 unsigned char *return_hash,
31 SilcUInt32 *return_hash_len,
34 silc_ske_select_security_properties(SilcSKE ske,
36 SilcSKEStartPayload payload,
37 SilcSKEStartPayload remote_payload);
39 silc_ske_process_key_material_data(unsigned char *data,
41 SilcUInt32 req_iv_len,
42 SilcUInt32 req_enc_key_len,
43 SilcUInt32 req_hmac_key_len,
46 silc_ske_process_key_material(SilcSKE ske,
47 SilcUInt32 req_iv_len,
48 SilcUInt32 req_enc_key_len,
49 SilcUInt32 req_hmac_key_len);
50 static void silc_ske_packet_receive(SilcPacketEngine engine,
51 SilcPacketStream stream,
53 void *callback_context,
55 static void silc_ske_packet_eos(SilcPacketEngine engine,
56 SilcPacketStream stream,
57 void *callback_context,
59 static void silc_ske_packet_error(SilcPacketEngine engine,
60 SilcPacketStream stream,
61 SilcPacketError error,
62 void *callback_context,
65 /* Structure to hold all SKE callbacks. */
66 struct SilcSKECallbacksStruct {
67 SilcSKEVerifyCb verify_key;
68 SilcSKECheckVersionCb check_version;
69 SilcSKECompletionCb completed;
73 /* Packet stream callbacks */
74 static SilcPacketCallbacks silc_ske_stream_cbs =
76 silc_ske_packet_receive,
81 /* Allocates new SKE object. */
83 SilcSKE silc_ske_alloc(SilcRng rng, SilcSchedule schedule, void *context)
87 SILC_LOG_DEBUG(("Allocating new Key Exchange object"));
89 if (!rng || !schedule)
92 ske = silc_calloc(1, sizeof(*ske));
95 ske->status = SILC_SKE_STATUS_OK;
97 ske->user_data = context;
98 ske->schedule = schedule;
104 /* Free's SKE object. */
106 void silc_ske_free(SilcSKE ske)
109 if (ske->users > 0) {
110 SILC_LOG_DEBUG(("Key Exchange set to FREED status"));
111 ske->status = SILC_SKE_STATUS_FREED;
115 SILC_LOG_DEBUG(("Freeing Key Exchange object"));
118 /* Free start payload */
119 if (ske->start_payload)
120 silc_ske_payload_start_free(ske->start_payload);
122 /* Free KE payload */
123 if (ske->ke1_payload)
124 silc_ske_payload_ke_free(ske->ke1_payload);
125 if (ske->ke2_payload)
126 silc_ske_payload_ke_free(ske->ke2_payload);
127 silc_free(ske->remote_version);
131 if (ske->prop->group)
132 silc_ske_group_free(ske->prop->group);
134 silc_pkcs_free(ske->prop->pkcs);
135 if (ske->prop->cipher)
136 silc_cipher_free(ske->prop->cipher);
138 silc_hash_free(ske->prop->hash);
140 silc_hmac_free(ske->prop->hmac);
141 silc_free(ske->prop);
143 if (ske->start_payload_copy)
144 silc_buffer_free(ske->start_payload_copy);
146 silc_mp_uninit(ske->x);
150 silc_mp_uninit(ske->KEY);
153 silc_free(ske->hash);
154 silc_free(ske->callbacks);
156 memset(ske, 'F', sizeof(*ske));
161 /* Return user context */
163 void *silc_ske_get_context(SilcSKE ske)
165 return ske->user_data;
168 /* Sets protocol callbacks */
170 void silc_ske_set_callbacks(SilcSKE ske,
171 SilcSKEVerifyCb verify_key,
172 SilcSKECheckVersionCb check_version,
173 SilcSKECompletionCb completed,
177 silc_free(ske->callbacks);
178 ske->callbacks = silc_calloc(1, sizeof(*ske->callbacks));
181 ske->callbacks->verify_key = verify_key;
182 ske->callbacks->check_version = check_version;
183 ske->callbacks->completed = completed;
184 ske->callbacks->context = context;
187 /* Aborts SKE protocol */
189 static void silc_ske_abort(SilcAsyncOperation op, void *context)
191 SilcSKE ske = context;
195 /* Public key verification completion callback */
197 static void silc_ske_pk_verified(SilcSKE ske, SilcSKEStatus status,
198 void *completion_context)
200 SILC_FSM_CALL_CONTINUE(&ske->fsm);
203 /* Initiator state machine */
204 SILC_FSM_STATE(silc_ske_st_initiator_start);
205 SILC_FSM_STATE(silc_ske_st_initiator_phase1);
206 SILC_FSM_STATE(silc_ske_st_initiator_phase2);
207 SILC_FSM_STATE(silc_ske_st_initiator_phase3);
208 SILC_FSM_STATE(silc_ske_st_initiator_phase4);
209 SILC_FSM_STATE(silc_ske_st_initiator_end);
210 SILC_FSM_STATE(silc_ske_st_initiator_aborted);
211 SILC_FSM_STATE(silc_ske_st_initiator_error);
213 /* Start protocol. Send our proposal */
215 SILC_FSM_STATE(silc_ske_st_initiator_start)
217 SilcSKE ske = fsm_context;
218 SilcBuffer payload_buf;
221 SILC_LOG_DEBUG(("Start"));
225 silc_fsm_next(fsm, silc_ske_st_initiator_aborted);
226 return SILC_FSM_CONTINUE;
229 /* Encode the payload */
230 status = silc_ske_payload_start_encode(ske, ske->start_payload,
232 if (status != SILC_SKE_STATUS_OK) {
233 /** Error encoding Start Payload */
234 ske->status = status;
235 silc_fsm_next(fsm, silc_ske_st_initiator_error);
236 return SILC_FSM_CONTINUE;
239 /* Save the the payload buffer for future use. It is later used to
240 compute the HASH value. */
241 ske->start_payload_copy = payload_buf;
243 /* Send the packet */
246 /** Wait for responder proposal */
247 SILC_LOG_DEBUG(("Waiting for reponder proposal"));
248 silc_fsm_next(ske, silc_ske_st_initiator_phase1);
249 return SILC_FSM_WAIT;
252 /* Phase-1. Receives responder's proposal */
254 SILC_FSM_STATE(silc_ske_st_initiator_phase1)
256 SilcSKE ske = fsm_context;
257 SilcSKEStatus status;
258 SilcSKEStartPayload payload;
259 SilcSKESecurityProperties prop;
260 SilcSKEDiffieHellmanGroup group;
262 SILC_LOG_DEBUG(("Start"));
266 silc_fsm_next(fsm, silc_ske_st_initiator_aborted);
267 return SILC_FSM_CONTINUE;
270 /* Decode the payload */
271 status = silc_ske_payload_start_decode(ske, ske->packet_buf, &payload);
272 if (status != SILC_SKE_STATUS_OK) {
273 /** Error decoding Start Payload */
274 ske->status = status;
275 silc_fsm_next(fsm, silc_ske_st_initiator_error);
276 return SILC_FSM_CONTINUE;
279 /* Check that the cookie is returned unmodified */
280 if (memcmp(ske->start_payload->cookie, payload->cookie,
281 ske->start_payload->cookie_len)) {
282 /** Invalid cookie */
283 SILC_LOG_ERROR(("Responder modified our cookie and it must not do it"));
284 ske->status = SILC_SKE_STATUS_INVALID_COOKIE;
285 silc_fsm_next(fsm, silc_ske_st_initiator_error);
286 return SILC_FSM_CONTINUE;
289 /* Check version string */
290 if (ske->callbacks->check_version) {
291 status = ske->callbacks->check_version(ske, payload->version,
292 payload->version_len,
293 ske->callbacks->context);
294 if (status != SILC_SKE_STATUS_OK) {
295 /** Version mismatch */
296 ske->status = status;
297 silc_fsm_next(fsm, silc_ske_st_initiator_error);
298 return SILC_FSM_CONTINUE;
302 /* Free our KE Start Payload context, we don't need it anymore. */
303 silc_ske_payload_start_free(ske->start_payload);
304 ske->start_payload = NULL;
306 /* Take the selected security properties into use while doing
307 the key exchange. This is used only while doing the key
309 ske->prop = prop = silc_calloc(1, sizeof(*prop));
312 prop->flags = payload->flags;
313 status = silc_ske_group_get_by_name(payload->ke_grp_list, &group);
314 if (status != SILC_SKE_STATUS_OK)
319 if (silc_pkcs_alloc(payload->pkcs_alg_list, &prop->pkcs) == FALSE) {
320 status = SILC_SKE_STATUS_UNKNOWN_PKCS;
323 if (silc_cipher_alloc(payload->enc_alg_list, &prop->cipher) == FALSE) {
324 status = SILC_SKE_STATUS_UNKNOWN_CIPHER;
327 if (silc_hash_alloc(payload->hash_alg_list, &prop->hash) == FALSE) {
328 status = SILC_SKE_STATUS_UNKNOWN_HASH_FUNCTION;
331 if (silc_hmac_alloc(payload->hmac_alg_list, NULL, &prop->hmac) == FALSE) {
332 status = SILC_SKE_STATUS_UNKNOWN_HMAC;
336 /* Save remote's KE Start Payload */
337 ske->start_payload = payload;
339 /** Send KE Payload */
340 silc_fsm_next(fsm, silc_ske_st_initiator_phase2);
341 return SILC_FSM_CONTINUE;
345 silc_ske_payload_start_free(payload);
347 silc_ske_group_free(group);
350 silc_pkcs_free(prop->pkcs);
352 silc_cipher_free(prop->cipher);
354 silc_hash_free(prop->hash);
356 silc_hmac_free(prop->hmac);
360 if (status == SILC_SKE_STATUS_OK)
361 status = SILC_SKE_STATUS_ERROR;
364 ske->status = status;
365 silc_fsm_next(fsm, silc_ske_st_initiator_error);
366 return SILC_FSM_CONTINUE;
369 /* Phase-2. Send KE payload */
371 SILC_FSM_STATE(silc_ske_st_initiator_phase2)
373 SilcSKE ske = fsm_context;
374 SilcSKEStatus status;
375 SilcBuffer payload_buf;
377 SilcSKEKEPayload payload;
380 SILC_LOG_DEBUG(("Start"));
382 /* Create the random number x, 1 < x < q. */
383 x = silc_calloc(1, sizeof(*x));
386 ske->status = SILC_SKE_STATUS_OUT_OF_MEMORY;
387 silc_fsm_next(fsm, silc_ske_st_initiator_error);
388 return SILC_FSM_CONTINUE;
392 silc_ske_create_rnd(ske, &ske->prop->group->group_order,
393 silc_mp_sizeinbase(&ske->prop->group->group_order, 2),
395 if (status != SILC_SKE_STATUS_OK) {
396 /** Error generating random number */
399 ske->status = status;
400 silc_fsm_next(fsm, silc_ske_st_initiator_error);
401 return SILC_FSM_CONTINUE;
404 /* Encode the result to Key Exchange Payload. */
406 payload = silc_calloc(1, sizeof(*payload));
411 ske->status = SILC_SKE_STATUS_OUT_OF_MEMORY;
412 silc_fsm_next(fsm, silc_ske_st_initiator_error);
413 return SILC_FSM_CONTINUE;
415 ske->ke1_payload = payload;
417 SILC_LOG_DEBUG(("Computing e = g ^ x mod p"));
419 /* Do the Diffie Hellman computation, e = g ^ x mod p */
420 silc_mp_init(&payload->x);
421 silc_mp_pow_mod(&payload->x, &ske->prop->group->generator, x,
422 &ske->prop->group->group);
425 if (ske->public_key) {
426 payload->pk_data = silc_pkcs_public_key_encode(ske->public_key, &pk_len);
427 if (!payload->pk_data) {
428 /** Error encoding public key */
431 silc_mp_uninit(&payload->x);
433 ske->ke1_payload = NULL;
434 ske->status = SILC_SKE_STATUS_ERROR;
435 silc_fsm_next(fsm, silc_ske_st_initiator_error);
436 return SILC_FSM_CONTINUE;
438 payload->pk_len = pk_len;
440 payload->pk_type = ske->pk_type;
442 /* Compute signature data if we are doing mutual authentication */
443 if (ske->private_key &&
444 ske->start_payload->flags & SILC_SKE_SP_FLAG_MUTUAL) {
445 unsigned char hash[SILC_HASH_MAXLEN], sign[2048 + 1];
446 SilcUInt32 hash_len, sign_len;
448 SILC_LOG_DEBUG(("We are doing mutual authentication"));
449 SILC_LOG_DEBUG(("Computing HASH_i value"));
451 /* Compute the hash value */
452 memset(hash, 0, sizeof(hash));
453 silc_ske_make_hash(ske, hash, &hash_len, TRUE);
455 SILC_LOG_DEBUG(("Signing HASH_i value"));
457 /* Sign the hash value */
458 silc_pkcs_private_key_data_set(ske->prop->pkcs, ske->private_key->prv,
459 ske->private_key->prv_len);
460 if (silc_pkcs_get_key_len(ske->prop->pkcs) / 8 > sizeof(sign) - 1 ||
461 !silc_pkcs_sign(ske->prop->pkcs, hash, hash_len, sign, &sign_len)) {
462 /** Error computing signature */
465 silc_mp_uninit(&payload->x);
466 silc_free(payload->pk_data);
468 ske->ke1_payload = NULL;
469 ske->status = SILC_SKE_STATUS_SIGNATURE_ERROR;
470 silc_fsm_next(fsm, silc_ske_st_initiator_error);
471 return SILC_FSM_CONTINUE;
473 payload->sign_data = silc_memdup(sign, sign_len);
474 payload->sign_len = sign_len;
475 memset(sign, 0, sizeof(sign));
478 status = silc_ske_payload_ke_encode(ske, payload, &payload_buf);
479 if (status != SILC_SKE_STATUS_OK) {
480 /** Error encoding KE payload */
483 silc_mp_uninit(&payload->x);
484 silc_free(payload->pk_data);
485 silc_free(payload->sign_data);
487 ske->ke1_payload = NULL;
488 ske->status = status;
489 silc_fsm_next(fsm, silc_ske_st_initiator_error);
490 return SILC_FSM_CONTINUE;
495 /* Send the packet. */
498 silc_buffer_free(payload_buf);
500 /** Waiting responder's KE payload */
501 silc_fsm_next(fsm, silc_ske_st_initiator_phase3);
502 return SILC_FSM_WAIT;
505 /* Phase-3. Process responder's KE payload */
507 SILC_FSM_STATE(silc_ske_st_initiator_phase3)
509 SilcSKE ske = fsm_context;
510 SilcSKEStatus status;
511 SilcSKEKEPayload payload;
514 SILC_LOG_DEBUG(("Start"));
518 silc_fsm_next(fsm, silc_ske_st_initiator_aborted);
519 return SILC_FSM_CONTINUE;
522 /* Decode the payload */
523 status = silc_ske_payload_ke_decode(ske, ske->packet_buf, &payload);
524 if (status != SILC_SKE_STATUS_OK) {
525 /** Error decoding KE payload */
526 ske->status = status;
527 silc_fsm_next(fsm, silc_ske_st_initiator_error);
528 return SILC_FSM_CONTINUE;
530 ske->ke2_payload = payload;
532 if (!payload->pk_data && ske->callbacks->verify_key) {
533 SILC_LOG_DEBUG(("Remote end did not send its public key (or certificate), "
534 "even though we require it"));
535 ske->status = SILC_SKE_STATUS_PUBLIC_KEY_NOT_PROVIDED;
539 SILC_LOG_DEBUG(("Computing KEY = f ^ x mod p"));
541 /* Compute the shared secret key */
542 KEY = silc_calloc(1, sizeof(*KEY));
544 silc_mp_pow_mod(KEY, &payload->x, ske->x, &ske->prop->group->group);
547 if (payload->pk_data && ske->callbacks->verify_key) {
548 SILC_LOG_DEBUG(("Verifying public key"));
550 /** Waiting public key verification */
551 silc_fsm_next(fsm, silc_ske_st_initiator_phase4);
552 SILC_FSM_CALL(ske->callbacks->verify_key(ske, payload->pk_data,
555 ske->callbacks->context,
556 silc_ske_pk_verified, NULL));
560 /** Process key material */
561 silc_fsm_next(fsm, silc_ske_st_initiator_phase4);
562 return SILC_FSM_CONTINUE;
565 silc_ske_payload_ke_free(payload);
566 ske->ke2_payload = NULL;
568 silc_mp_uninit(ske->KEY);
572 if (status == SILC_SKE_STATUS_OK)
573 return SILC_SKE_STATUS_ERROR;
576 ske->status = status;
577 silc_fsm_next(fsm, silc_ske_st_initiator_error);
578 return SILC_FSM_CONTINUE;
581 /* Process key material */
583 SILC_FSM_STATE(silc_ske_st_initiator_phase4)
585 SilcSKE ske = fsm_context;
586 SilcSKEStatus status;
587 SilcSKEKEPayload payload;
588 unsigned char hash[SILC_HASH_MAXLEN];
590 SilcPublicKey public_key = NULL;
591 int key_len, block_len;
595 silc_fsm_next(fsm, silc_ske_st_initiator_aborted);
596 return SILC_FSM_CONTINUE;
599 /* Check result of public key verification */
600 if (ske->status != SILC_SKE_STATUS_OK) {
601 /** Public key not verified */
602 SILC_LOG_DEBUG(("Public key verification failed"));
603 silc_fsm_next(fsm, silc_ske_st_initiator_error);
604 return SILC_FSM_CONTINUE;
607 payload = ske->ke2_payload;
609 if (payload->pk_data) {
610 /* Decode the public key */
611 if (!silc_pkcs_public_key_decode(payload->pk_data, payload->pk_len,
613 SILC_LOG_ERROR(("Unsupported/malformed public key received"));
614 status = SILC_SKE_STATUS_UNSUPPORTED_PUBLIC_KEY;
618 SILC_LOG_DEBUG(("Public key is authentic"));
620 /* Compute the hash value */
621 status = silc_ske_make_hash(ske, hash, &hash_len, FALSE);
622 if (status != SILC_SKE_STATUS_OK)
625 ske->hash = silc_memdup(hash, hash_len);
626 ske->hash_len = hash_len;
628 SILC_LOG_DEBUG(("Verifying signature (HASH)"));
630 /* Verify signature */
631 silc_pkcs_public_key_set(ske->prop->pkcs, public_key);
632 if (silc_pkcs_verify(ske->prop->pkcs, payload->sign_data,
633 payload->sign_len, hash, hash_len) == FALSE) {
634 SILC_LOG_ERROR(("Signature verification failed, incorrect signature"));
635 status = SILC_SKE_STATUS_INCORRECT_SIGNATURE;
639 SILC_LOG_DEBUG(("Signature is Ok"));
641 silc_pkcs_public_key_free(public_key);
642 memset(hash, 'F', hash_len);
645 ske->status = SILC_SKE_STATUS_OK;
647 /* Process key material */
648 key_len = silc_cipher_get_key_len(ske->prop->cipher);
649 block_len = silc_cipher_get_key_len(ske->prop->cipher);
650 hash_len = silc_hash_len(ske->prop->hash);
651 ske->keymat = silc_ske_process_key_material(ske, block_len,
654 SILC_LOG_ERROR(("Error processing key material"));
655 status = SILC_SKE_STATUS_ERROR;
659 /* Send SUCCESS packet */
662 /** Waiting completion */
663 silc_fsm_next(fsm, silc_ske_st_initiator_end);
664 return SILC_FSM_WAIT;
667 memset(hash, 'F', sizeof(hash));
668 silc_ske_payload_ke_free(payload);
669 ske->ke2_payload = NULL;
671 silc_mp_uninit(ske->KEY);
676 silc_pkcs_public_key_free(public_key);
679 memset(ske->hash, 'F', hash_len);
680 silc_free(ske->hash);
684 if (status == SILC_SKE_STATUS_OK)
685 status = SILC_SKE_STATUS_ERROR;
688 ske->status = status;
689 silc_fsm_next(fsm, silc_ske_st_initiator_error);
690 return SILC_FSM_CONTINUE;
693 /* Protocol completed */
695 SILC_FSM_STATE(silc_ske_st_initiator_end)
697 SilcSKE ske = fsm_context;
701 silc_fsm_next(fsm, silc_ske_st_initiator_aborted);
702 return SILC_FSM_CONTINUE;
705 /* Call the completion callback */
706 if (ske->callbacks->completed)
707 ske->callbacks->completed(ske, ske->status, NULL, NULL, NULL, NULL);
709 return SILC_FSM_FINISH;
712 /* Aborted by application */
714 SILC_FSM_STATE(silc_ske_st_initiator_aborted)
717 return SILC_FSM_FINISH;
722 SILC_FSM_STATE(silc_ske_st_initiator_error)
725 return SILC_FSM_FINISH;
729 static void silc_ske_initiator_finished(SilcFSM fsm, void *fsm_context,
730 void *destructor_context)
735 /* Starts the protocol as initiator */
738 silc_ske_initiator_start(SilcSKE ske,
739 SilcPacketStream stream,
740 SilcSKEStartPayload start_payload)
742 SILC_LOG_DEBUG(("Start SKE as initiator"));
744 if (!ske || !stream || !start_payload)
747 if (!silc_async_init(&ske->op, silc_ske_abort, NULL, ske))
750 if (!silc_fsm_init(&ske->fsm, ske, silc_ske_initiator_finished, ske,
754 ske->start_payload = start_payload;
756 /* Link to packet stream to get key exchange packets */
757 ske->stream = stream;
758 silc_packet_stream_ref(ske->stream);
759 silc_packet_stream_callbacks(ske->stream, &silc_ske_stream_cbs, ske);
761 /* Start SKE as initiator */
762 silc_fsm_start(&ske->fsm, silc_ske_st_initiator_start);
767 /* Responder state machine */
768 SILC_FSM_STATE(silc_ske_st_responder_start);
769 SILC_FSM_STATE(silc_ske_st_responder_phase1);
770 SILC_FSM_STATE(silc_ske_st_responder_phase2);
771 SILC_FSM_STATE(silc_ske_st_responder_phase3);
772 SILC_FSM_STATE(silc_ske_st_responder_phase4);
773 SILC_FSM_STATE(silc_ske_st_responder_end);
774 SILC_FSM_STATE(silc_ske_st_responder_aborted);
775 SILC_FSM_STATE(silc_ske_st_responder_error);
777 /* Start protocol as responder. Decode initiator's start payload */
779 SILC_FSM_STATE(silc_ske_st_responder_start)
781 SilcSKE ske = fsm_context;
782 SilcSKEStatus status;
783 SilcSKEStartPayload remote_payload = NULL, payload = NULL;
785 SILC_LOG_DEBUG(("Start"));
789 silc_fsm_next(fsm, silc_ske_st_responder_aborted);
790 return SILC_FSM_CONTINUE;
793 /* Decode the payload */
794 status = silc_ske_payload_start_decode(ske, ske->packet_buf,
796 if (status != SILC_SKE_STATUS_OK) {
797 /** Error decoding Start Payload */
798 ske->status = status;
799 silc_fsm_next(fsm, silc_ske_st_responder_error);
800 return SILC_FSM_CONTINUE;
803 /* Take a copy of the payload buffer for future use. It is used to
804 compute the HASH value. */
805 ske->start_payload_copy = silc_buffer_copy(ske->packet_buf);
807 /* Force the mutual authentication flag if we want to do it. */
808 if (ske->flags & SILC_SKE_SP_FLAG_MUTUAL) {
809 SILC_LOG_DEBUG(("Force mutual authentication"));
810 remote_payload->flags |= SILC_SKE_SP_FLAG_MUTUAL;
813 /* Force PFS flag if we require it */
814 if (ske->flags & SILC_SKE_SP_FLAG_PFS) {
815 SILC_LOG_DEBUG(("Force PFS"));
816 remote_payload->flags |= SILC_SKE_SP_FLAG_PFS;
819 /* Disable IV Included flag if requested */
820 if (remote_payload->flags & SILC_SKE_SP_FLAG_IV_INCLUDED &&
821 !(ske->flags & SILC_SKE_SP_FLAG_IV_INCLUDED)) {
822 SILC_LOG_DEBUG(("We do not support IV Included flag"));
823 remote_payload->flags &= ~SILC_SKE_SP_FLAG_IV_INCLUDED;
826 /* Parse and select the security properties from the payload */
827 payload = silc_calloc(1, sizeof(*payload));
828 status = silc_ske_select_security_properties(ske, ske->version,
829 payload, remote_payload);
830 if (status != SILC_SKE_STATUS_OK) {
831 /** Error selecting proposal */
833 silc_ske_payload_start_free(remote_payload);
835 ske->status = status;
836 silc_fsm_next(fsm, silc_ske_st_responder_error);
837 return SILC_FSM_CONTINUE;
840 ske->start_payload = payload;
842 silc_ske_payload_start_free(remote_payload);
844 /** Send proposal to initiator */
845 silc_fsm_next(fsm, silc_ske_st_responder_phase1);
846 return SILC_FSM_CONTINUE;
849 /* Phase-1. Send Start Payload */
851 SILC_FSM_STATE(silc_ske_st_responder_phase1)
853 SilcSKE ske = fsm_context;
854 SilcSKEStatus status;
855 SilcBuffer payload_buf;
856 SilcSKESecurityProperties prop;
857 SilcSKEDiffieHellmanGroup group = NULL;
859 SILC_LOG_DEBUG(("Start"));
861 /* Allocate security properties from the payload. These are allocated
862 only for this negotiation and will be free'd after KE is over. */
863 ske->prop = prop = silc_calloc(1, sizeof(*prop));
864 prop->flags = ske->start_payload->flags;
865 status = silc_ske_group_get_by_name(ske->start_payload->ke_grp_list, &group);
866 if (status != SILC_SKE_STATUS_OK)
871 if (silc_pkcs_alloc(ske->start_payload->pkcs_alg_list,
872 &prop->pkcs) == FALSE) {
873 status = SILC_SKE_STATUS_UNKNOWN_PKCS;
876 if (silc_cipher_alloc(ske->start_payload->enc_alg_list,
877 &prop->cipher) == FALSE) {
878 status = SILC_SKE_STATUS_UNKNOWN_CIPHER;
881 if (silc_hash_alloc(ske->start_payload->hash_alg_list,
882 &prop->hash) == FALSE) {
883 status = SILC_SKE_STATUS_UNKNOWN_HASH_FUNCTION;
886 if (silc_hmac_alloc(ske->start_payload->hmac_alg_list, NULL,
887 &prop->hmac) == FALSE) {
888 status = SILC_SKE_STATUS_UNKNOWN_HMAC;
892 /* Encode the payload */
893 status = silc_ske_payload_start_encode(ske, ske->start_payload,
895 if (status != SILC_SKE_STATUS_OK)
898 /* Send the packet. */
901 silc_buffer_free(payload_buf);
903 /** Waiting initiator's KE payload */
904 silc_fsm_next(fsm, silc_ske_st_responder_phase2);
905 return SILC_FSM_WAIT;
909 silc_ske_group_free(group);
912 silc_pkcs_free(prop->pkcs);
914 silc_cipher_free(prop->cipher);
916 silc_hash_free(prop->hash);
918 silc_hmac_free(prop->hmac);
922 if (status == SILC_SKE_STATUS_OK)
923 status = SILC_SKE_STATUS_ERROR;
926 ske->status = status;
927 silc_fsm_next(fsm, silc_ske_st_responder_error);
928 return SILC_FSM_CONTINUE;
931 /* Phase-2. Decode initiator's KE payload */
933 SILC_FSM_STATE(silc_ske_st_responder_phase2)
935 SilcSKE ske = fsm_context;
936 SilcSKEStatus status;
937 SilcSKEKEPayload recv_payload;
939 SILC_LOG_DEBUG(("Start"));
943 silc_fsm_next(fsm, silc_ske_st_responder_aborted);
944 return SILC_FSM_CONTINUE;
947 /* Decode Key Exchange Payload */
948 status = silc_ske_payload_ke_decode(ske, ske->packet_buf, &recv_payload);
949 if (status != SILC_SKE_STATUS_OK) {
950 /** Error decoding KE payload */
951 ske->status = status;
952 silc_fsm_next(fsm, silc_ske_st_responder_error);
953 return SILC_FSM_CONTINUE;
956 ske->ke1_payload = recv_payload;
958 /* Verify the received public key and verify the signature if we are
959 doing mutual authentication. */
960 if (ske->start_payload &&
961 ske->start_payload->flags & SILC_SKE_SP_FLAG_MUTUAL) {
963 SILC_LOG_DEBUG(("We are doing mutual authentication"));
965 if (!recv_payload->pk_data && ske->callbacks->verify_key) {
966 /** Public key not provided */
967 SILC_LOG_ERROR(("Remote end did not send its public key (or "
968 "certificate), even though we require it"));
969 ske->status = SILC_SKE_STATUS_PUBLIC_KEY_NOT_PROVIDED;
970 silc_fsm_next(fsm, silc_ske_st_responder_error);
971 return SILC_FSM_CONTINUE;
974 if (recv_payload->pk_data && ske->callbacks->verify_key) {
975 SILC_LOG_DEBUG(("Verifying public key"));
977 /** Waiting public key verification */
978 silc_fsm_next(fsm, silc_ske_st_responder_phase3);
979 SILC_FSM_CALL(ske->callbacks->verify_key(ske, recv_payload->pk_data,
980 recv_payload->pk_len,
981 recv_payload->pk_type,
982 ske->callbacks->context,
983 silc_ske_pk_verified, NULL));
988 /** Generate KE2 payload */
989 silc_fsm_next(fsm, silc_ske_st_responder_phase3);
990 return SILC_FSM_CONTINUE;
993 /* Phase-3. Generate KE2 payload */
995 SILC_FSM_STATE(silc_ske_st_responder_phase3)
997 SilcSKE ske = fsm_context;
998 SilcSKEStatus status;
999 SilcSKEKEPayload recv_payload, send_payload;
1004 silc_fsm_next(fsm, silc_ske_st_responder_aborted);
1005 return SILC_FSM_CONTINUE;
1008 /* Check result of public key verification */
1009 if (ske->status != SILC_SKE_STATUS_OK) {
1010 /** Public key not verified */
1011 SILC_LOG_DEBUG(("Public key verification failed"));
1012 silc_fsm_next(fsm, silc_ske_st_initiator_error);
1013 return SILC_FSM_CONTINUE;
1016 recv_payload = ske->ke1_payload;
1018 /* The public key verification was performed only if the Mutual
1019 Authentication flag is set. */
1020 if (ske->start_payload &&
1021 ske->start_payload->flags & SILC_SKE_SP_FLAG_MUTUAL) {
1022 SilcPublicKey public_key = NULL;
1023 unsigned char hash[SILC_HASH_MAXLEN];
1024 SilcUInt32 hash_len;
1026 /* Decode the public key */
1027 if (!silc_pkcs_public_key_decode(recv_payload->pk_data,
1028 recv_payload->pk_len,
1030 /** Error decoding public key */
1031 SILC_LOG_ERROR(("Unsupported/malformed public key received"));
1032 ske->status = SILC_SKE_STATUS_UNSUPPORTED_PUBLIC_KEY;
1033 silc_fsm_next(fsm, silc_ske_st_responder_error);
1034 return SILC_FSM_CONTINUE;
1037 SILC_LOG_DEBUG(("Public key is authentic"));
1039 /* Compute the hash value */
1040 status = silc_ske_make_hash(ske, hash, &hash_len, TRUE);
1041 if (status != SILC_SKE_STATUS_OK) {
1042 /** Error computing hash */
1043 ske->status = status;
1044 silc_fsm_next(fsm, silc_ske_st_responder_error);
1045 return SILC_FSM_CONTINUE;
1048 SILC_LOG_DEBUG(("Verifying signature (HASH_i)"));
1050 /* Verify signature */
1051 silc_pkcs_public_key_set(ske->prop->pkcs, public_key);
1052 if (silc_pkcs_verify(ske->prop->pkcs, recv_payload->sign_data,
1053 recv_payload->sign_len, hash, hash_len) == FALSE) {
1054 /** Incorrect signature */
1055 SILC_LOG_ERROR(("Signature verification failed, incorrect signature"));
1056 ske->status = SILC_SKE_STATUS_INCORRECT_SIGNATURE;
1057 silc_fsm_next(fsm, silc_ske_st_responder_error);
1058 return SILC_FSM_CONTINUE;
1061 SILC_LOG_DEBUG(("Signature is Ok"));
1063 silc_pkcs_public_key_free(public_key);
1064 memset(hash, 'F', hash_len);
1067 /* Create the random number x, 1 < x < q. */
1068 x = silc_calloc(1, sizeof(*x));
1071 silc_ske_create_rnd(ske, &ske->prop->group->group_order,
1072 silc_mp_sizeinbase(&ske->prop->group->group_order, 2),
1074 if (status != SILC_SKE_STATUS_OK) {
1075 /** Error generating random number */
1078 ske->status = status;
1079 silc_fsm_next(fsm, silc_ske_st_responder_error);
1080 return SILC_FSM_CONTINUE;
1083 /* Save the results for later processing */
1084 send_payload = silc_calloc(1, sizeof(*send_payload));
1086 ske->ke2_payload = send_payload;
1088 SILC_LOG_DEBUG(("Computing f = g ^ x mod p"));
1090 /* Do the Diffie Hellman computation, f = g ^ x mod p */
1091 silc_mp_init(&send_payload->x);
1092 silc_mp_pow_mod(&send_payload->x, &ske->prop->group->generator, x,
1093 &ske->prop->group->group);
1095 SILC_LOG_DEBUG(("Computing KEY = e ^ x mod p"));
1097 /* Compute the shared secret key */
1098 KEY = silc_calloc(1, sizeof(*KEY));
1100 silc_mp_pow_mod(KEY, &ske->ke1_payload->x, ske->x,
1101 &ske->prop->group->group);
1104 /** Send KE2 payload */
1105 silc_fsm_next(fsm, silc_ske_st_responder_phase4);
1106 return SILC_FSM_CONTINUE;
1109 /* Phase-4. Send KE2 payload */
1111 SILC_FSM_STATE(silc_ske_st_responder_phase4)
1113 SilcSKE ske = fsm_context;
1114 SilcSKEStatus status;
1115 SilcBuffer payload_buf;
1116 unsigned char hash[SILC_HASH_MAXLEN], sign[2048 + 1], *pk;
1117 SilcUInt32 hash_len, sign_len, pk_len;
1119 SILC_LOG_DEBUG(("Start"));
1121 if (ske->public_key && ske->private_key) {
1122 SILC_LOG_DEBUG(("Getting public key"));
1124 /* Get the public key */
1125 pk = silc_pkcs_public_key_encode(ske->public_key, &pk_len);
1127 /** Error encoding public key */
1128 status = SILC_SKE_STATUS_OUT_OF_MEMORY;
1129 silc_fsm_next(fsm, silc_ske_st_responder_error);
1130 return SILC_FSM_CONTINUE;
1132 ske->ke2_payload->pk_data = pk;
1133 ske->ke2_payload->pk_len = pk_len;
1135 SILC_LOG_DEBUG(("Computing HASH value"));
1137 /* Compute the hash value */
1138 memset(hash, 0, sizeof(hash));
1139 status = silc_ske_make_hash(ske, hash, &hash_len, FALSE);
1140 if (status != SILC_SKE_STATUS_OK) {
1141 /** Error computing hash */
1142 ske->status = status;
1143 silc_fsm_next(fsm, silc_ske_st_responder_error);
1144 return SILC_FSM_CONTINUE;
1147 ske->hash = silc_memdup(hash, hash_len);
1148 ske->hash_len = hash_len;
1150 SILC_LOG_DEBUG(("Signing HASH value"));
1152 /* Sign the hash value */
1153 silc_pkcs_private_key_data_set(ske->prop->pkcs, ske->private_key->prv,
1154 ske->private_key->prv_len);
1155 if (silc_pkcs_get_key_len(ske->prop->pkcs) / 8 > sizeof(sign) - 1 ||
1156 !silc_pkcs_sign(ske->prop->pkcs, hash, hash_len, sign, &sign_len)) {
1157 /** Error computing signature */
1158 status = SILC_SKE_STATUS_SIGNATURE_ERROR;
1159 silc_fsm_next(fsm, silc_ske_st_responder_error);
1160 return SILC_FSM_CONTINUE;
1162 ske->ke2_payload->sign_data = silc_memdup(sign, sign_len);
1163 ske->ke2_payload->sign_len = sign_len;
1164 memset(sign, 0, sizeof(sign));
1166 ske->ke2_payload->pk_type = ske->pk_type;
1168 /* Encode the Key Exchange Payload */
1169 status = silc_ske_payload_ke_encode(ske, ske->ke2_payload,
1171 if (status != SILC_SKE_STATUS_OK) {
1172 /** Error encoding KE payload */
1173 ske->status = status;
1174 silc_fsm_next(fsm, silc_ske_st_responder_error);
1175 return SILC_FSM_CONTINUE;
1178 /* Send the packet. */
1181 silc_buffer_free(payload_buf);
1183 /** Waiting completion */
1184 silc_fsm_next(fsm, silc_ske_st_responder_end);
1185 return SILC_FSM_WAIT;
1188 /* Protocol completed */
1190 SILC_FSM_STATE(silc_ske_st_responder_end)
1192 SilcSKE ske = fsm_context;
1196 silc_fsm_next(fsm, silc_ske_st_responder_aborted);
1197 return SILC_FSM_CONTINUE;
1200 /* Call the completion callback */
1201 if (ske->callbacks->completed)
1202 ske->callbacks->completed(ske, ske->status, NULL, NULL, NULL, NULL);
1204 return SILC_FSM_FINISH;
1207 /* Aborted by application */
1209 SILC_FSM_STATE(silc_ske_st_responder_aborted)
1214 return SILC_FSM_FINISH;
1217 /* Error occurred */
1219 SILC_FSM_STATE(silc_ske_st_responder_error)
1224 return SILC_FSM_FINISH;
1228 static void silc_ske_responder_finished(SilcFSM fsm, void *fsm_context,
1229 void *destructor_context)
1234 /* Starts the protocol as responder. */
1237 silc_ske_responder_start(SilcSKE ske,
1238 SilcPacketStream stream,
1239 const char *version,
1240 SilcBuffer start_payload,
1241 SilcSKESecurityPropertyFlag flags)
1243 SILC_LOG_DEBUG(("Start SKE as responder"));
1245 if (!ske || !stream || !start_payload)
1248 if (!silc_async_init(&ske->op, silc_ske_abort, NULL, ske))
1251 if (!silc_fsm_init(&ske->fsm, ske, silc_ske_responder_finished, ske,
1255 ske->packet_buf = start_payload;
1257 ske->version = strdup(version);
1259 /* Link to packet stream to get key exchange packets */
1260 ske->stream = stream;
1261 silc_packet_stream_ref(ske->stream);
1262 silc_packet_stream_callbacks(ske->stream, &silc_ske_stream_cbs, ske);
1264 /* Start SKE as responder */
1265 silc_fsm_start(&ske->fsm, silc_ske_st_initiator_start);
1270 SILC_FSM_STATE(silc_ske_st_rekey_initiator_start);
1272 SILC_FSM_STATE(silc_ske_st_rekey_initiator_start)
1277 /* Starts rekey protocol as initiator */
1280 silc_ske_rekey_initiator_start(SilcSKE ske,
1281 SilcPacketStream stream,
1282 SilcSKERekeyMaterial rekey)
1284 SILC_LOG_DEBUG(("Start SKE rekey as initator"));
1286 if (!ske || !stream || !rekey)
1289 if (!silc_async_init(&ske->op, silc_ske_abort, NULL, ske))
1292 if (!silc_fsm_init(&ske->fsm, ske, NULL, NULL, ske->schedule))
1297 /* Link to packet stream to get key exchange packets */
1298 ske->stream = stream;
1299 silc_packet_stream_ref(ske->stream);
1300 silc_packet_stream_callbacks(ske->stream, &silc_ske_stream_cbs, ske);
1302 /* Start SKE rekey as initiator */
1303 silc_fsm_start(&ske->fsm, silc_ske_st_rekey_initiator_start);
1308 SILC_FSM_STATE(silc_ske_st_rekey_responder_start);
1310 SILC_FSM_STATE(silc_ske_st_rekey_responder_start)
1315 /* Starts rekey protocol as responder */
1318 silc_ske_rekey_responder_start(SilcSKE ske,
1319 SilcPacketStream stream,
1320 SilcBuffer ke_payload,
1321 SilcSKERekeyMaterial rekey)
1323 SILC_LOG_DEBUG(("Start SKE rekey as responder"));
1325 if (!ske || !stream || !rekey)
1327 if (rekey->pfs && !ke_payload)
1330 if (!silc_async_init(&ske->op, silc_ske_abort, NULL, ske))
1333 if (!silc_fsm_init(&ske->fsm, ske, NULL, NULL, ske->schedule))
1336 ske->packet_buf = ke_payload;
1339 /* Link to packet stream to get key exchange packets */
1340 ske->stream = stream;
1341 silc_packet_stream_ref(ske->stream);
1342 silc_packet_stream_callbacks(ske->stream, &silc_ske_stream_cbs, ske);
1344 /* Start SKE rekey as responder */
1345 silc_fsm_start(&ske->fsm, silc_ske_st_rekey_responder_start);
1350 /* Assembles security properties */
1353 silc_ske_assemble_security_properties(SilcSKE ske,
1354 SilcSKESecurityPropertyFlag flags,
1355 const char *version)
1357 SilcSKEStartPayload rp;
1360 SILC_LOG_DEBUG(("Assembling KE Start Payload"));
1362 rp = silc_calloc(1, sizeof(*rp));
1365 rp->flags = (unsigned char)flags;
1367 /* Set random cookie */
1368 rp->cookie = silc_calloc(SILC_SKE_COOKIE_LEN, sizeof(*rp->cookie));
1369 for (i = 0; i < SILC_SKE_COOKIE_LEN; i++)
1370 rp->cookie[i] = silc_rng_get_byte_fast(ske->rng);
1371 rp->cookie_len = SILC_SKE_COOKIE_LEN;
1374 rp->version = strdup(version);
1375 rp->version_len = strlen(version);
1377 /* Get supported Key Exhange groups */
1378 rp->ke_grp_list = silc_ske_get_supported_groups();
1379 rp->ke_grp_len = strlen(rp->ke_grp_list);
1381 /* Get supported PKCS algorithms */
1382 rp->pkcs_alg_list = silc_pkcs_get_supported();
1383 rp->pkcs_alg_len = strlen(rp->pkcs_alg_list);
1385 /* Get supported encryption algorithms */
1386 rp->enc_alg_list = silc_cipher_get_supported();
1387 rp->enc_alg_len = strlen(rp->enc_alg_list);
1389 /* Get supported hash algorithms */
1390 rp->hash_alg_list = silc_hash_get_supported();
1391 rp->hash_alg_len = strlen(rp->hash_alg_list);
1393 /* Get supported HMACs */
1394 rp->hmac_alg_list = silc_hmac_get_supported();
1395 rp->hmac_alg_len = strlen(rp->hmac_alg_list);
1398 /* Get supported compression algorithms */
1399 rp->comp_alg_list = strdup("none");
1400 rp->comp_alg_len = strlen("none");
1402 rp->len = 1 + 1 + 2 + SILC_SKE_COOKIE_LEN +
1403 2 + rp->version_len +
1404 2 + rp->ke_grp_len + 2 + rp->pkcs_alg_len +
1405 2 + rp->enc_alg_len + 2 + rp->hash_alg_len +
1406 2 + rp->hmac_alg_len + 2 + rp->comp_alg_len;
1411 /* Selects the supported security properties from the remote end's Key
1412 Exchange Start Payload. */
1414 static SilcSKEStatus
1415 silc_ske_select_security_properties(SilcSKE ske,
1416 const char *version,
1417 SilcSKEStartPayload payload,
1418 SilcSKEStartPayload remote_payload)
1420 SilcSKEStatus status;
1421 SilcSKEStartPayload rp;
1425 SILC_LOG_DEBUG(("Parsing KE Start Payload"));
1427 rp = remote_payload;
1429 /* Check version string */
1430 if (ske->callbacks->check_version) {
1431 status = ske->callbacks->check_version(ske, rp->version,
1433 ske->callbacks->context);
1434 if (status != SILC_SKE_STATUS_OK) {
1435 ske->status = status;
1440 ske->remote_version = silc_memdup(rp->version, rp->version_len);
1442 /* Flags are returned unchanged. */
1443 payload->flags = rp->flags;
1445 /* Take cookie, we must return it to sender unmodified. */
1446 payload->cookie = silc_calloc(SILC_SKE_COOKIE_LEN, sizeof(unsigned char));
1447 payload->cookie_len = SILC_SKE_COOKIE_LEN;
1448 memcpy(payload->cookie, rp->cookie, SILC_SKE_COOKIE_LEN);
1450 /* Put our version to our reply */
1451 payload->version = strdup(version);
1452 payload->version_len = strlen(version);
1454 /* Get supported Key Exchange groups */
1455 cp = rp->ke_grp_list;
1456 if (cp && strchr(cp, ',')) {
1460 len = strcspn(cp, ",");
1461 item = silc_calloc(len + 1, sizeof(char));
1462 memcpy(item, cp, len);
1464 SILC_LOG_DEBUG(("Proposed KE group `%s'", item));
1466 if (silc_ske_group_get_by_name(item, NULL) == SILC_SKE_STATUS_OK) {
1467 SILC_LOG_DEBUG(("Found KE group `%s'", item));
1469 payload->ke_grp_len = len;
1470 payload->ke_grp_list = item;
1475 if (strlen(cp) == 0)
1484 if (!payload->ke_grp_len && !payload->ke_grp_list) {
1485 SILC_LOG_DEBUG(("Could not find supported KE group"));
1487 return SILC_SKE_STATUS_UNKNOWN_GROUP;
1491 if (!rp->ke_grp_len) {
1492 SILC_LOG_DEBUG(("KE group not defined in payload"));
1494 return SILC_SKE_STATUS_BAD_PAYLOAD;
1497 SILC_LOG_DEBUG(("Proposed KE group `%s'", rp->ke_grp_list));
1498 SILC_LOG_DEBUG(("Found KE group `%s'", rp->ke_grp_list));
1500 payload->ke_grp_len = rp->ke_grp_len;
1501 payload->ke_grp_list = strdup(rp->ke_grp_list);
1504 /* Get supported PKCS algorithms */
1505 cp = rp->pkcs_alg_list;
1506 if (cp && strchr(cp, ',')) {
1510 len = strcspn(cp, ",");
1511 item = silc_calloc(len + 1, sizeof(char));
1512 memcpy(item, cp, len);
1514 SILC_LOG_DEBUG(("Proposed PKCS alg `%s'", item));
1516 if (silc_pkcs_is_supported(item) == TRUE) {
1517 SILC_LOG_DEBUG(("Found PKCS alg `%s'", item));
1519 payload->pkcs_alg_len = len;
1520 payload->pkcs_alg_list = item;
1525 if (strlen(cp) == 0)
1534 if (!payload->pkcs_alg_len && !payload->pkcs_alg_list) {
1535 SILC_LOG_DEBUG(("Could not find supported PKCS alg"));
1536 silc_free(payload->ke_grp_list);
1538 return SILC_SKE_STATUS_UNKNOWN_PKCS;
1542 if (!rp->pkcs_alg_len) {
1543 SILC_LOG_DEBUG(("PKCS alg not defined in payload"));
1544 silc_free(payload->ke_grp_list);
1546 return SILC_SKE_STATUS_BAD_PAYLOAD;
1549 SILC_LOG_DEBUG(("Proposed PKCS alg `%s'", rp->pkcs_alg_list));
1550 SILC_LOG_DEBUG(("Found PKCS alg `%s'", rp->pkcs_alg_list));
1552 payload->pkcs_alg_len = rp->pkcs_alg_len;
1553 payload->pkcs_alg_list = strdup(rp->pkcs_alg_list);
1556 /* Get supported encryption algorithms */
1557 cp = rp->enc_alg_list;
1558 if (cp && strchr(cp, ',')) {
1562 len = strcspn(cp, ",");
1563 item = silc_calloc(len + 1, sizeof(char));
1564 memcpy(item, cp, len);
1566 SILC_LOG_DEBUG(("Proposed encryption alg `%s'", item));
1568 if (silc_cipher_is_supported(item) == TRUE) {
1569 SILC_LOG_DEBUG(("Found encryption alg `%s'", item));
1571 payload->enc_alg_len = len;
1572 payload->enc_alg_list = item;
1577 if (strlen(cp) == 0)
1586 if (!payload->enc_alg_len && !payload->enc_alg_list) {
1587 SILC_LOG_DEBUG(("Could not find supported encryption alg"));
1588 silc_free(payload->ke_grp_list);
1589 silc_free(payload->pkcs_alg_list);
1591 return SILC_SKE_STATUS_UNKNOWN_CIPHER;
1595 if (!rp->enc_alg_len) {
1596 SILC_LOG_DEBUG(("Encryption alg not defined in payload"));
1597 silc_free(payload->ke_grp_list);
1598 silc_free(payload->pkcs_alg_list);
1600 return SILC_SKE_STATUS_BAD_PAYLOAD;
1603 SILC_LOG_DEBUG(("Proposed encryption alg `%s' and selected it",
1606 payload->enc_alg_len = rp->enc_alg_len;
1607 payload->enc_alg_list = strdup(rp->enc_alg_list);
1610 /* Get supported hash algorithms */
1611 cp = rp->hash_alg_list;
1612 if (cp && strchr(cp, ',')) {
1616 len = strcspn(cp, ",");
1617 item = silc_calloc(len + 1, sizeof(char));
1618 memcpy(item, cp, len);
1620 SILC_LOG_DEBUG(("Proposed hash alg `%s'", item));
1622 if (silc_hash_is_supported(item) == TRUE) {
1623 SILC_LOG_DEBUG(("Found hash alg `%s'", item));
1625 payload->hash_alg_len = len;
1626 payload->hash_alg_list = item;
1631 if (strlen(cp) == 0)
1640 if (!payload->hash_alg_len && !payload->hash_alg_list) {
1641 SILC_LOG_DEBUG(("Could not find supported hash alg"));
1642 silc_free(payload->ke_grp_list);
1643 silc_free(payload->pkcs_alg_list);
1644 silc_free(payload->enc_alg_list);
1646 return SILC_SKE_STATUS_UNKNOWN_HASH_FUNCTION;
1650 if (!rp->hash_alg_len) {
1651 SILC_LOG_DEBUG(("Hash alg not defined in payload"));
1652 silc_free(payload->ke_grp_list);
1653 silc_free(payload->pkcs_alg_list);
1654 silc_free(payload->enc_alg_list);
1656 return SILC_SKE_STATUS_BAD_PAYLOAD;
1659 SILC_LOG_DEBUG(("Proposed hash alg `%s' and selected it",
1660 rp->hash_alg_list));
1662 payload->hash_alg_len = rp->hash_alg_len;
1663 payload->hash_alg_list = strdup(rp->hash_alg_list);
1666 /* Get supported HMACs */
1667 cp = rp->hmac_alg_list;
1668 if (cp && strchr(cp, ',')) {
1672 len = strcspn(cp, ",");
1673 item = silc_calloc(len + 1, sizeof(char));
1674 memcpy(item, cp, len);
1676 SILC_LOG_DEBUG(("Proposed HMAC `%s'", item));
1678 if (silc_hmac_is_supported(item) == TRUE) {
1679 SILC_LOG_DEBUG(("Found HMAC `%s'", item));
1681 payload->hmac_alg_len = len;
1682 payload->hmac_alg_list = item;
1687 if (strlen(cp) == 0)
1696 if (!payload->hmac_alg_len && !payload->hmac_alg_list) {
1697 SILC_LOG_DEBUG(("Could not find supported HMAC"));
1698 silc_free(payload->ke_grp_list);
1699 silc_free(payload->pkcs_alg_list);
1700 silc_free(payload->enc_alg_list);
1701 silc_free(payload->hash_alg_list);
1703 return SILC_SKE_STATUS_UNKNOWN_HMAC;
1707 if (!rp->hmac_alg_len) {
1708 SILC_LOG_DEBUG(("HMAC not defined in payload"));
1709 silc_free(payload->ke_grp_list);
1710 silc_free(payload->pkcs_alg_list);
1711 silc_free(payload->enc_alg_list);
1712 silc_free(payload->hash_alg_list);
1714 return SILC_SKE_STATUS_BAD_PAYLOAD;
1717 SILC_LOG_DEBUG(("Proposed HMAC `%s' and selected it",
1718 rp->hmac_alg_list));
1720 payload->hmac_alg_len = rp->hmac_alg_len;
1721 payload->hmac_alg_list = strdup(rp->hmac_alg_list);
1724 /* Get supported compression algorithms */
1725 cp = rp->comp_alg_list;
1726 if (cp && strchr(cp, ',')) {
1730 len = strcspn(cp, ",");
1731 item = silc_calloc(len + 1, sizeof(char));
1732 memcpy(item, cp, len);
1734 SILC_LOG_DEBUG(("Proposed Compression `%s'", item));
1737 if (!strcmp(item, "none")) {
1738 SILC_LOG_DEBUG(("Found Compression `%s'", item));
1739 payload->comp_alg_len = len;
1740 payload->comp_alg_list = item;
1744 if (silc_hmac_is_supported(item) == TRUE) {
1745 SILC_LOG_DEBUG(("Found Compression `%s'", item));
1746 payload->comp_alg_len = len;
1747 payload->comp_alg_list = item;
1753 if (strlen(cp) == 0)
1763 payload->len = 1 + 1 + 2 + SILC_SKE_COOKIE_LEN +
1764 2 + payload->version_len +
1765 2 + payload->ke_grp_len + 2 + payload->pkcs_alg_len +
1766 2 + payload->enc_alg_len + 2 + payload->hash_alg_len +
1767 2 + payload->hmac_alg_len + 2 + payload->comp_alg_len;
1769 return SILC_SKE_STATUS_OK;
1772 /* Creates random number such that 1 < rnd < n and at most length
1773 of len bits. The rnd sent as argument must be initialized. */
1775 static SilcSKEStatus silc_ske_create_rnd(SilcSKE ske, SilcMPInt *n,
1779 SilcSKEStatus status = SILC_SKE_STATUS_OK;
1780 unsigned char *string;
1784 return SILC_SKE_STATUS_ERROR;
1786 SILC_LOG_DEBUG(("Creating random number"));
1788 l = ((len - 1) / 8);
1790 /* Get the random number as string */
1791 string = silc_rng_get_rn_data(ske->rng, l);
1793 return SILC_SKE_STATUS_OUT_OF_MEMORY;
1795 /* Decode the string into a MP integer */
1796 silc_mp_bin2mp(string, l, rnd);
1797 silc_mp_mod_2exp(rnd, rnd, len);
1800 if (silc_mp_cmp_ui(rnd, 1) < 0)
1801 status = SILC_SKE_STATUS_ERROR;
1802 if (silc_mp_cmp(rnd, n) >= 0)
1803 status = SILC_SKE_STATUS_ERROR;
1805 memset(string, 'F', l);
1811 /* Creates a hash value HASH as defined in the SKE protocol. If the
1812 `initiator' is TRUE then this function is used to create the HASH_i
1813 hash value defined in the protocol. If it is FALSE then this is used
1814 to create the HASH value defined by the protocol. */
1816 static SilcSKEStatus silc_ske_make_hash(SilcSKE ske,
1817 unsigned char *return_hash,
1818 SilcUInt32 *return_hash_len,
1821 SilcSKEStatus status = SILC_SKE_STATUS_OK;
1823 unsigned char *e, *f, *KEY;
1824 SilcUInt32 e_len, f_len, KEY_len;
1827 SILC_LOG_DEBUG(("Start"));
1829 if (initiator == FALSE) {
1830 e = silc_mp_mp2bin(&ske->ke1_payload->x, 0, &e_len);
1831 f = silc_mp_mp2bin(&ske->ke2_payload->x, 0, &f_len);
1832 KEY = silc_mp_mp2bin(ske->KEY, 0, &KEY_len);
1834 /* Format the buffer used to compute the hash value */
1835 buf = silc_buffer_alloc_size(silc_buffer_len(ske->start_payload_copy) +
1836 ske->ke2_payload->pk_len +
1837 ske->ke1_payload->pk_len +
1838 e_len + f_len + KEY_len);
1840 return SILC_SKE_STATUS_OUT_OF_MEMORY;
1842 /* Initiator is not required to send its public key */
1843 if (!ske->ke1_payload->pk_data) {
1845 silc_buffer_format(buf,
1846 SILC_STR_UI_XNSTRING(
1847 ske->start_payload_copy->data,
1848 silc_buffer_len(ske->start_payload_copy)),
1849 SILC_STR_UI_XNSTRING(ske->ke2_payload->pk_data,
1850 ske->ke2_payload->pk_len),
1851 SILC_STR_UI_XNSTRING(e, e_len),
1852 SILC_STR_UI_XNSTRING(f, f_len),
1853 SILC_STR_UI_XNSTRING(KEY, KEY_len),
1857 silc_buffer_format(buf,
1858 SILC_STR_UI_XNSTRING(
1859 ske->start_payload_copy->data,
1860 silc_buffer_len(ske->start_payload_copy)),
1861 SILC_STR_UI_XNSTRING(ske->ke2_payload->pk_data,
1862 ske->ke2_payload->pk_len),
1863 SILC_STR_UI_XNSTRING(ske->ke1_payload->pk_data,
1864 ske->ke1_payload->pk_len),
1865 SILC_STR_UI_XNSTRING(e, e_len),
1866 SILC_STR_UI_XNSTRING(f, f_len),
1867 SILC_STR_UI_XNSTRING(KEY, KEY_len),
1871 silc_buffer_free(buf);
1872 memset(e, 0, e_len);
1873 memset(f, 0, f_len);
1874 memset(KEY, 0, KEY_len);
1878 return SILC_SKE_STATUS_ERROR;
1881 memset(e, 0, e_len);
1882 memset(f, 0, f_len);
1883 memset(KEY, 0, KEY_len);
1888 e = silc_mp_mp2bin(&ske->ke1_payload->x, 0, &e_len);
1890 buf = silc_buffer_alloc_size(silc_buffer_len(ske->start_payload_copy) +
1891 ske->ke1_payload->pk_len + e_len);
1893 return SILC_SKE_STATUS_OUT_OF_MEMORY;
1895 /* Format the buffer used to compute the hash value */
1897 silc_buffer_format(buf,
1898 SILC_STR_UI_XNSTRING(ske->start_payload_copy->data,
1899 silc_buffer_len(ske->start_payload_copy)),
1900 SILC_STR_UI_XNSTRING(ske->ke1_payload->pk_data,
1901 ske->ke1_payload->pk_len),
1902 SILC_STR_UI_XNSTRING(e, e_len),
1905 silc_buffer_free(buf);
1906 memset(e, 0, e_len);
1908 return SILC_SKE_STATUS_ERROR;
1911 memset(e, 0, e_len);
1916 silc_hash_make(ske->prop->hash, buf->data, silc_buffer_len(buf),
1918 *return_hash_len = silc_hash_len(ske->prop->hash);
1920 if (initiator == FALSE) {
1921 SILC_LOG_HEXDUMP(("HASH"), return_hash, *return_hash_len);
1923 SILC_LOG_HEXDUMP(("HASH_i"), return_hash, *return_hash_len);
1926 silc_buffer_free(buf);
1931 /* Processes the provided key material `data' as the SILC protocol
1932 specification defines. */
1935 silc_ske_process_key_material_data(unsigned char *data,
1936 SilcUInt32 data_len,
1937 SilcUInt32 req_iv_len,
1938 SilcUInt32 req_enc_key_len,
1939 SilcUInt32 req_hmac_key_len,
1943 unsigned char hashd[SILC_HASH_MAXLEN];
1944 SilcUInt32 hash_len = req_hmac_key_len;
1945 SilcUInt32 enc_key_len = req_enc_key_len / 8;
1946 SilcSKEKeyMaterial key;
1948 SILC_LOG_DEBUG(("Start"));
1950 if (!req_iv_len || !req_enc_key_len || !req_hmac_key_len)
1953 buf = silc_buffer_alloc_size(1 + data_len);
1956 silc_buffer_format(buf,
1957 SILC_STR_UI_CHAR(0),
1958 SILC_STR_UI_XNSTRING(data, data_len),
1962 memset(hashd, 0, sizeof(hashd));
1964 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
1965 key->send_iv = silc_calloc(req_iv_len, sizeof(unsigned char));
1966 memcpy(key->send_iv, hashd, req_iv_len);
1967 memset(hashd, 0, sizeof(hashd));
1969 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
1970 key->receive_iv = silc_calloc(req_iv_len, sizeof(unsigned char));
1971 memcpy(key->receive_iv, hashd, req_iv_len);
1972 key->iv_len = req_iv_len;
1974 /* Take the encryption keys. If requested key size is more than
1975 the size of hash length we will distribute more key material
1976 as protocol defines. */
1978 if (enc_key_len > hash_len) {
1980 unsigned char k1[SILC_HASH_MAXLEN], k2[SILC_HASH_MAXLEN],
1981 k3[SILC_HASH_MAXLEN];
1982 unsigned char *dtmp;
1985 if (enc_key_len > (3 * hash_len))
1988 /* Take first round */
1989 memset(k1, 0, sizeof(k1));
1990 silc_hash_make(hash, buf->data, silc_buffer_len(buf), k1);
1992 /* Take second round */
1993 dist = silc_buffer_alloc_size(data_len + hash_len);
1996 silc_buffer_format(dist,
1997 SILC_STR_UI_XNSTRING(data, data_len),
1998 SILC_STR_UI_XNSTRING(k1, hash_len),
2000 memset(k2, 0, sizeof(k2));
2001 silc_hash_make(hash, dist->data, silc_buffer_len(dist), k2);
2003 /* Take third round */
2004 dist = silc_buffer_realloc(dist, data_len + hash_len + hash_len);
2005 silc_buffer_pull_tail(dist, hash_len);
2006 silc_buffer_pull(dist, data_len + hash_len);
2007 silc_buffer_format(dist,
2008 SILC_STR_UI_XNSTRING(k2, hash_len),
2010 silc_buffer_push(dist, data_len + hash_len);
2011 memset(k3, 0, sizeof(k3));
2012 silc_hash_make(hash, dist->data, silc_buffer_len(dist), k3);
2014 /* Then, save the keys */
2015 dtmp = silc_calloc((3 * hash_len), sizeof(unsigned char));
2016 memcpy(dtmp, k1, hash_len);
2017 memcpy(dtmp + hash_len, k2, hash_len);
2018 memcpy(dtmp + hash_len + hash_len, k3, hash_len);
2020 key->send_enc_key = silc_calloc(enc_key_len, sizeof(unsigned char));
2021 memcpy(key->send_enc_key, dtmp, enc_key_len);
2022 key->enc_key_len = req_enc_key_len;
2024 memset(dtmp, 0, (3 * hash_len));
2025 memset(k1, 0, sizeof(k1));
2026 memset(k2, 0, sizeof(k2));
2027 memset(k3, 0, sizeof(k3));
2029 silc_buffer_clear(dist);
2030 silc_buffer_free(dist);
2032 /* Take normal hash as key */
2033 memset(hashd, 0, sizeof(hashd));
2034 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
2035 key->send_enc_key = silc_calloc(enc_key_len, sizeof(unsigned char));
2036 memcpy(key->send_enc_key, hashd, enc_key_len);
2037 key->enc_key_len = req_enc_key_len;
2041 if (enc_key_len > hash_len) {
2043 unsigned char k1[SILC_HASH_MAXLEN], k2[SILC_HASH_MAXLEN],
2044 k3[SILC_HASH_MAXLEN];
2045 unsigned char *dtmp;
2048 if (enc_key_len > (3 * hash_len))
2051 /* Take first round */
2052 memset(k1, 0, sizeof(k1));
2053 silc_hash_make(hash, buf->data, silc_buffer_len(buf), k1);
2055 /* Take second round */
2056 dist = silc_buffer_alloc_size(data_len + hash_len);
2059 silc_buffer_format(dist,
2060 SILC_STR_UI_XNSTRING(data, data_len),
2061 SILC_STR_UI_XNSTRING(k1, hash_len),
2063 memset(k2, 0, sizeof(k2));
2064 silc_hash_make(hash, dist->data, silc_buffer_len(dist), k2);
2066 /* Take third round */
2067 dist = silc_buffer_realloc(dist, data_len + hash_len + hash_len);
2068 silc_buffer_pull_tail(dist, hash_len);
2069 silc_buffer_pull(dist, data_len + hash_len);
2070 silc_buffer_format(dist,
2071 SILC_STR_UI_XNSTRING(k2, hash_len),
2073 silc_buffer_push(dist, data_len + hash_len);
2074 memset(k3, 0, sizeof(k3));
2075 silc_hash_make(hash, dist->data, silc_buffer_len(dist), k3);
2077 /* Then, save the keys */
2078 dtmp = silc_calloc((3 * hash_len), sizeof(unsigned char));
2079 memcpy(dtmp, k1, hash_len);
2080 memcpy(dtmp + hash_len, k2, hash_len);
2081 memcpy(dtmp + hash_len + hash_len, k3, hash_len);
2083 key->receive_enc_key = silc_calloc(enc_key_len, sizeof(unsigned char));
2084 memcpy(key->receive_enc_key, dtmp, enc_key_len);
2085 key->enc_key_len = req_enc_key_len;
2087 memset(dtmp, 0, (3 * hash_len));
2088 memset(k1, 0, sizeof(k1));
2089 memset(k2, 0, sizeof(k2));
2090 memset(k3, 0, sizeof(k3));
2092 silc_buffer_clear(dist);
2093 silc_buffer_free(dist);
2095 /* Take normal hash as key */
2096 memset(hashd, 0, sizeof(hashd));
2097 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
2098 key->receive_enc_key = silc_calloc(enc_key_len, sizeof(unsigned char));
2099 memcpy(key->receive_enc_key, hashd, enc_key_len);
2100 key->enc_key_len = req_enc_key_len;
2103 /* Take HMAC keys */
2104 memset(hashd, 0, sizeof(hashd));
2106 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
2107 key->send_hmac_key = silc_calloc(req_hmac_key_len, sizeof(unsigned char));
2108 memcpy(key->send_hmac_key, hashd, req_hmac_key_len);
2109 memset(hashd, 0, sizeof(hashd));
2111 silc_hash_make(hash, buf->data, silc_buffer_len(buf), hashd);
2112 key->receive_hmac_key = silc_calloc(req_hmac_key_len, sizeof(unsigned char));
2113 memcpy(key->receive_hmac_key, hashd, req_hmac_key_len);
2114 key->hmac_key_len = req_hmac_key_len;
2115 memset(hashd, 0, sizeof(hashd));
2117 silc_buffer_clear(buf);
2118 silc_buffer_free(buf);
2123 /* Processes negotiated key material as protocol specifies. This returns
2124 the actual keys to be used in the SILC. */
2127 silc_ske_process_key_material(SilcSKE ske,
2128 SilcUInt32 req_iv_len,
2129 SilcUInt32 req_enc_key_len,
2130 SilcUInt32 req_hmac_key_len)
2132 SilcSKEStatus status;
2134 unsigned char *tmpbuf;
2136 SilcSKEKeyMaterial key;
2138 /* Encode KEY to binary data */
2139 tmpbuf = silc_mp_mp2bin(ske->KEY, 0, &klen);
2141 buf = silc_buffer_alloc_size(klen + ske->hash_len);
2144 silc_buffer_format(buf,
2145 SILC_STR_UI_XNSTRING(tmpbuf, klen),
2146 SILC_STR_UI_XNSTRING(ske->hash, ske->hash_len),
2149 /* Process the key material */
2150 key = silc_ske_process_key_material_data(buf->data, silc_buffer_len(buf),
2151 req_iv_len, req_enc_key_len,
2155 memset(tmpbuf, 0, klen);
2157 silc_buffer_clear(buf);
2158 silc_buffer_free(buf);
2163 /* Free key material structure */
2165 void silc_ske_free_key_material(SilcSKEKeyMaterial key)
2171 silc_free(key->send_iv);
2172 if (key->receive_iv)
2173 silc_free(key->receive_iv);
2174 if (key->send_enc_key) {
2175 memset(key->send_enc_key, 0, key->enc_key_len / 8);
2176 silc_free(key->send_enc_key);
2178 if (key->receive_enc_key) {
2179 memset(key->receive_enc_key, 0, key->enc_key_len / 8);
2180 silc_free(key->receive_enc_key);
2182 if (key->send_hmac_key) {
2183 memset(key->send_hmac_key, 0, key->hmac_key_len);
2184 silc_free(key->send_hmac_key);
2186 if (key->receive_hmac_key) {
2187 memset(key->receive_hmac_key, 0, key->hmac_key_len);
2188 silc_free(key->receive_hmac_key);
2193 const char *silc_ske_status_string[] =
2197 "Unkown error occurred",
2198 "Bad payload in packet",
2199 "Unsupported group",
2200 "Unsupported cipher",
2202 "Unsupported hash function",
2204 "Unsupported public key (or certificate)",
2205 "Incorrect signature",
2206 "Bad or unsupported version",
2211 "Remote did not provide public key",
2212 "Key exchange protocol is not active",
2213 "Bad reserved field in packet",
2214 "Bad payload length in packet",
2215 "Error computing signature",
2216 "System out of memory",
2221 /* Maps status to readable string and returns the string. If string is not
2222 found and empty character string ("") is returned. */
2224 const char *silc_ske_map_status(SilcSKEStatus status)
2228 for (i = 0; silc_ske_status_string[i]; i++)
2230 return silc_ske_status_string[i];
2235 /* Parses remote host's version string. */
2237 bool silc_ske_parse_version(SilcSKE ske,
2238 SilcUInt32 *protocol_version,
2239 char **protocol_version_string,
2240 SilcUInt32 *software_version,
2241 char **software_version_string,
2242 char **vendor_version)
2244 return silc_parse_version_string(ske->remote_version,
2246 protocol_version_string,
2248 software_version_string,