*** empty log message ***
[gnutls.git] / lib / gnutls_handshake.c
blobab6dba515fb7d87780a92360b8f1fa31b21e35e7
1 /*
2 * Copyright (C) 2000,2001,2002 Nikos Mavroyanopoulos
4 * This file is part of GNUTLS.
6 * The GNUTLS library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 #include "gnutls_int.h"
23 #include "gnutls_errors.h"
24 #include "gnutls_dh.h"
25 #include "debug.h"
26 #include "gnutls_algorithms.h"
27 #include "gnutls_compress.h"
28 #include "gnutls_cipher.h"
29 #include "gnutls_buffers.h"
30 #include "gnutls_kx.h"
31 #include "gnutls_handshake.h"
32 #include "gnutls_num.h"
33 #include "gnutls_hash_int.h"
34 #include "gnutls_db.h"
35 #include "gnutls_extensions.h"
36 #include "gnutls_random.h"
37 #include "gnutls_auth_int.h"
38 #include "gnutls_v2_compat.h"
39 #include "auth_cert.h"
40 #include "gnutls_cert.h"
41 #include "gnutls_constate.h"
42 #include <gnutls_record.h>
43 #include <gnutls_alert.h>
44 #include <gnutls_state.h>
46 #ifdef HANDSHAKE_DEBUG
47 #define ERR(x, y) _gnutls_handshake_log( "HSK: %s (%d)\n", x,y)
48 #else
49 #define ERR(x, y)
50 #endif
52 #define TRUE 1
53 #define FALSE 0
55 int _gnutls_server_select_comp_method(GNUTLS_STATE state,
56 opaque * data, int datalen);
59 /* Clears the handshake hash buffers and handles.
61 inline static
62 void _gnutls_handshake_hash_buffers_clear( GNUTLS_STATE state) {
63 _gnutls_hash_deinit( state->gnutls_internals.handshake_mac_handle_md5, NULL);
64 _gnutls_hash_deinit( state->gnutls_internals.handshake_mac_handle_sha, NULL);
65 state->gnutls_internals.handshake_mac_handle_md5 = NULL;
66 state->gnutls_internals.handshake_mac_handle_sha = NULL;
67 _gnutls_handshake_buffer_clear( state);
70 /* this will copy the required values for resuming to
71 * gnutls_internals, and to security_parameters.
72 * this will keep as less data to security_parameters.
74 static void resume_copy_required_values(GNUTLS_STATE state)
76 /* get the new random values */
77 memcpy(state->gnutls_internals.resumed_security_parameters.
78 server_random,
79 state->security_parameters.server_random, TLS_RANDOM_SIZE);
80 memcpy(state->gnutls_internals.resumed_security_parameters.
81 client_random,
82 state->security_parameters.client_random, TLS_RANDOM_SIZE);
84 /* keep the ciphersuite and compression
85 * That is because the client must see these in our
86 * hello message.
88 memcpy(state->security_parameters.current_cipher_suite.
89 CipherSuite,
90 state->gnutls_internals.resumed_security_parameters.
91 current_cipher_suite.CipherSuite, 2);
93 state->gnutls_internals.compression_method = state->gnutls_internals.resumed_security_parameters.read_compression_algorithm; /* or write_compression_algorithm
94 * they are the same
97 state->security_parameters.entity =
98 state->gnutls_internals.resumed_security_parameters.entity;
100 _gnutls_set_current_version( state, state->gnutls_internals.resumed_security_parameters.version);
102 state->security_parameters.cert_type =
103 state->gnutls_internals.resumed_security_parameters.cert_type;
105 memcpy(state->security_parameters.session_id,
106 state->gnutls_internals.resumed_security_parameters.
107 session_id, sizeof(state->security_parameters.session_id));
108 state->security_parameters.session_id_size =
109 state->gnutls_internals.resumed_security_parameters.
110 session_id_size;
112 return;
115 void _gnutls_set_server_random(GNUTLS_STATE state, uint8 * random)
117 memcpy(state->security_parameters.server_random, random,
118 TLS_RANDOM_SIZE);
121 void _gnutls_set_client_random(GNUTLS_STATE state, uint8 * random)
123 memcpy(state->security_parameters.client_random, random,
124 TLS_RANDOM_SIZE);
127 /* Calculate The SSL3 Finished message
129 #define SSL3_CLIENT_MSG "CLNT"
130 #define SSL3_SERVER_MSG "SRVR"
131 #define SSL_MSG_LEN 4
132 static int _gnutls_ssl3_finished(GNUTLS_STATE state, int type, opaque * ret)
134 const int siz = SSL_MSG_LEN;
135 GNUTLS_MAC_HANDLE td_md5;
136 GNUTLS_MAC_HANDLE td_sha;
137 char *mesg;
139 td_md5 = _gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_md5);
140 if (td_md5 == NULL) {
141 gnutls_assert();
142 return GNUTLS_E_HASH_FAILED;
145 td_sha = _gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_sha);
146 if (td_sha == NULL) {
147 gnutls_assert();
148 _gnutls_hash_deinit( td_md5, NULL);
149 return GNUTLS_E_HASH_FAILED;
152 if (type == GNUTLS_SERVER) {
153 mesg = SSL3_SERVER_MSG;
154 } else {
155 mesg = SSL3_CLIENT_MSG;
158 _gnutls_hash(td_md5, mesg, siz);
159 _gnutls_hash(td_sha, mesg, siz);
161 _gnutls_mac_deinit_ssl3_handshake(td_md5, ret, state->security_parameters.master_secret, TLS_MASTER_SIZE);
162 _gnutls_mac_deinit_ssl3_handshake(td_sha, &ret[16], state->security_parameters.master_secret, TLS_MASTER_SIZE);
164 return 0;
167 /* Hash the handshake messages as required by TLS 1.0
169 #define SERVER_MSG "server finished"
170 #define CLIENT_MSG "client finished"
171 #define TLS_MSG_LEN 15
172 int _gnutls_finished(GNUTLS_STATE state, int type, void *ret)
174 const int siz = TLS_MSG_LEN;
175 opaque concat[36];
176 opaque *mesg;
177 GNUTLS_MAC_HANDLE td_md5;
178 GNUTLS_MAC_HANDLE td_sha;
181 td_md5 = _gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_md5);
182 if (td_md5 == NULL) {
183 gnutls_assert();
184 return GNUTLS_E_HASH_FAILED;
187 td_sha = _gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_sha);
188 if (td_sha == NULL) {
189 gnutls_assert();
190 _gnutls_hash_deinit( td_md5, NULL);
191 return GNUTLS_E_HASH_FAILED;
195 _gnutls_hash_deinit(td_md5, concat);
196 _gnutls_hash_deinit(td_sha, &concat[16]);
198 if (type == GNUTLS_SERVER) {
199 mesg = SERVER_MSG;
200 } else {
201 mesg = CLIENT_MSG;
204 return _gnutls_PRF(state->security_parameters.master_secret,
205 TLS_MASTER_SIZE, mesg, siz, concat, 36,
206 12, ret);
209 /* this function will produce TLS_RANDOM_SIZE bytes of random data
210 * and put it to dst.
212 int _gnutls_create_random(opaque * dst)
214 uint32 tim;
215 opaque rand[TLS_RANDOM_SIZE - 4];
217 tim = time(NULL);
218 /* generate server random value */
219 _gnutls_write_uint32(tim, dst);
221 if (_gnutls_get_random
222 (rand, TLS_RANDOM_SIZE - 4, GNUTLS_STRONG_RANDOM) < 0) {
223 gnutls_assert();
224 return GNUTLS_E_MEMORY_ERROR;
226 memcpy(&dst[4], rand, 28);
228 return 0;
232 /* Read a client hello packet.
233 * A client hello must be a known version client hello
234 * or version 2.0 client hello (only for compatibility
235 * since SSL version 2.0 is not supported).
237 int _gnutls_read_client_hello(GNUTLS_STATE state, opaque * data,
238 int datalen)
240 uint8 session_id_len = 0, z;
241 int pos = 0;
242 int ret = 0;
243 uint16 sizeOfSuites;
244 GNUTLS_Version version;
245 int len = datalen;
246 opaque random[TLS_RANDOM_SIZE], *suite_ptr;
247 GNUTLS_Version ver;
249 if (state->gnutls_internals.v2_hello != 0) { /* version 2.0 */
250 return _gnutls_read_client_hello_v2(state, data, datalen);
252 DECR_LEN(len, 2);
254 _gnutls_handshake_log("HSK: Client's version: %d.%d\n", data[pos], data[pos + 1]);
256 version = _gnutls_version_get(data[pos], data[pos + 1]);
257 set_adv_version(state, data[pos], data[pos + 1]);
258 pos += 2;
260 /* if we do not support that version */
261 if (_gnutls_version_is_supported(state, version) == 0) {
262 /* If he requested something we do not support
263 * then we send him the lowest we support.
265 ver = _gnutls_version_lowest(state);
266 } else {
267 ver = version;
270 /* he should have send us the highest version
271 * he supports.
273 if (ver == GNUTLS_VERSION_UNKNOWN || ver > version) {
274 gnutls_assert();
275 return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
277 _gnutls_set_current_version(state, ver);
279 /* Read client random value.
281 DECR_LEN(len, TLS_RANDOM_SIZE);
282 _gnutls_set_client_random(state, &data[pos]);
283 pos += TLS_RANDOM_SIZE;
285 _gnutls_create_random(random);
286 _gnutls_set_server_random(state, random);
288 state->security_parameters.timestamp = time(NULL);
290 DECR_LEN(len, 1);
291 session_id_len = data[pos++];
293 /* RESUME SESSION
295 if (session_id_len > TLS_MAX_SESSION_ID_SIZE) {
296 gnutls_assert();
297 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
299 DECR_LEN(len, session_id_len);
300 ret = _gnutls_server_restore_session(state, &data[pos], session_id_len);
301 pos += session_id_len;
303 if (ret == 0) { /* resumed! */
304 resume_copy_required_values(state);
306 state->gnutls_internals.resumed = RESUME_TRUE;
307 return 0;
308 } else {
309 _gnutls_generate_session_id(state->security_parameters.
310 session_id,
311 &state->security_parameters.
312 session_id_size);
314 state->gnutls_internals.resumed = RESUME_FALSE;
317 /* Select a ciphersuite
319 DECR_LEN(len, 2);
320 sizeOfSuites = _gnutls_read_uint16(&data[pos]);
321 pos += 2;
323 DECR_LEN(len, sizeOfSuites);
324 suite_ptr = &data[pos];
325 pos += sizeOfSuites;
327 /* Select an appropriate compression method
329 DECR_LEN(len, 1);
330 z = data[pos++]; /* z is the number of compression methods */
332 DECR_LEN(len, z);
333 ret = _gnutls_server_select_comp_method(state, &data[pos], z);
334 pos += z;
336 if (ret < 0) {
337 gnutls_assert();
338 return ret;
341 /* Parse the extensions (if any)
343 if (ver >= GNUTLS_TLS1) {
344 ret = _gnutls_parse_extensions(state, &data[pos], len); /* len is the rest of the parsed length */
345 if (ret < 0) {
346 gnutls_assert();
347 return ret;
351 /* select an appropriate cipher suite
353 ret = _gnutls_server_select_suite(state, suite_ptr, sizeOfSuites);
354 if (ret < 0) {
355 gnutls_assert();
356 return ret;
359 return 0;
362 /* here we hash all pending data.
364 inline static int
365 _gnutls_handshake_hash_pending( GNUTLS_STATE state) {
366 int siz, ret;
367 char * data;
369 if (state->gnutls_internals.handshake_mac_handle_sha==NULL ||
370 state->gnutls_internals.handshake_mac_handle_md5==NULL) {
371 gnutls_assert();
372 return GNUTLS_E_INTERNAL_ERROR;
375 /* We check if there are pending data to hash.
377 if ((ret=_gnutls_handshake_buffer_get_ptr(state, &data, &siz)) < 0) {
378 gnutls_assert();
379 return ret;
382 if (siz > 0) {
383 _gnutls_hash( state->gnutls_internals.handshake_mac_handle_sha, data, siz);
384 _gnutls_hash( state->gnutls_internals.handshake_mac_handle_md5, data, siz);
387 _gnutls_handshake_buffer_empty( state);
389 return 0;
393 /* This is to be called after sending CHANGE CIPHER SPEC packet
394 * and initializing encryption. This is the first encrypted message
395 * we send.
397 int _gnutls_send_finished(GNUTLS_STATE state, int again)
399 uint8 data[36];
400 int ret=0;
401 int data_size = 0;
404 if (again == 0) {
406 /* This needed in order to hash all the required
407 * messages.
409 if ((ret=_gnutls_handshake_hash_pending(state)) < 0) {
410 gnutls_assert();
411 return ret;
414 if (gnutls_protocol_get_version( state) == GNUTLS_SSL3) {
415 ret =
416 _gnutls_ssl3_finished(state,
417 state->
418 security_parameters.
419 entity, data);
420 data_size = 36;
421 } else { /* TLS 1.0 */
422 ret =
423 _gnutls_finished(state,
424 state->security_parameters.
425 entity, data);
426 data_size = 12;
430 if (ret < 0) {
431 gnutls_assert();
432 return ret;
435 ret =
436 _gnutls_send_handshake(state, data, data_size,
437 GNUTLS_FINISHED);
439 return ret;
442 /* This is to be called after sending our finished message. If everything
443 * went fine we have negotiated a secure connection
445 int _gnutls_recv_finished(GNUTLS_STATE state)
447 uint8 data[36], *vrfy;
448 int data_size;
449 int ret;
450 int vrfysize;
452 ret = 0;
454 ret =
455 _gnutls_recv_handshake(state, &vrfy, &vrfysize,
456 GNUTLS_FINISHED, MANDATORY_PACKET);
457 if (ret < 0) {
458 ERR("recv finished int", ret);
459 gnutls_assert();
460 return ret;
464 if ( gnutls_protocol_get_version( state) == GNUTLS_SSL3) {
465 data_size = 36;
466 } else {
467 data_size = 12;
470 if (vrfysize != data_size) {
471 gnutls_assert();
472 return GNUTLS_E_ERROR_IN_FINISHED_PACKET;
475 if (gnutls_protocol_get_version( state) == GNUTLS_SSL3) {
476 ret =
477 _gnutls_ssl3_finished(state,
478 (state->security_parameters.
479 entity + 1) % 2, data);
480 } else { /* TLS 1.0 */
481 ret =
482 _gnutls_finished(state,
483 (state->security_parameters.entity +
484 1) % 2, data);
487 if (ret < 0) {
488 gnutls_assert();
489 return ret;
492 if (memcmp(vrfy, data, data_size) != 0) {
493 gnutls_assert();
494 ret = GNUTLS_E_ERROR_IN_FINISHED_PACKET;
496 gnutls_free(vrfy);
498 return ret;
501 /* returns PK_RSA if the given cipher suite list only supports,
502 * RSA algorithms, PK_DSA if DSS, and -1 if both or none.
504 int _gnutls_find_pk_algos_in_ciphersuites( opaque* data, int datalen) {
505 int j;
506 PKAlgorithm algo=-1, prev_algo = 0;
507 KXAlgorithm kx;
509 for (j = 0; j < datalen; j += 2) {
510 kx = _gnutls_cipher_suite_get_kx_algo(*((GNUTLS_CipherSuite *) & data[j]));
512 if ( _gnutls_map_kx_get_cred( kx) == GNUTLS_CRD_CERTIFICATE) {
513 algo = _gnutls_map_pk_get_pk( kx);
515 if (algo!=prev_algo && prev_algo!=0) return -1;
516 prev_algo = algo;
520 return algo;
524 /* This selects the best supported ciphersuite from the ones supported. Then
525 * it adds the suite into the state and performs some checks.
527 int _gnutls_server_select_suite(GNUTLS_STATE state, opaque *data, int datalen)
529 int x, i, j;
530 GNUTLS_CipherSuite *ciphers;
531 int retval, err;
532 PKAlgorithm pk_algo; /* will hold the pk algorithms
533 * supported by the peer.
536 pk_algo = _gnutls_find_pk_algos_in_ciphersuites( data, datalen);
538 x = _gnutls_supported_ciphersuites(state, &ciphers);
539 if (x<=0) {
540 gnutls_assert();
541 if (x<0) return x;
542 else return GNUTLS_E_INVALID_REQUEST;
545 /* Here we remove any ciphersuite that does not conform
546 * the certificate requested, or to the
547 * authentication requested (eg SRP).
549 x = _gnutls_remove_unwanted_ciphersuites(state, &ciphers, x, pk_algo);
550 if (x<=0) {
551 gnutls_assert();
552 if (x<0) return x;
553 else return GNUTLS_E_INSUFICIENT_CRED;
556 #ifdef HANDSHAKE_DEBUG
557 _gnutls_handshake_log("HSK: Requested cipher suites: \n");
558 for (j = 0; j < datalen; j += 2)
559 _gnutls_handshake_log("\t%s\n",
560 _gnutls_cipher_suite_get_name(*
561 ((GNUTLS_CipherSuite *) & data[j])));
562 _gnutls_handshake_log("HSK: Supported cipher suites: \n");
563 for (j = 0; j < x; j++)
564 _gnutls_handshake_log("\t%s\n",
565 _gnutls_cipher_suite_get_name(ciphers[j]));
566 #endif
567 memset(state->security_parameters.current_cipher_suite.CipherSuite, '\0', 2);
569 retval = GNUTLS_E_UNKNOWN_CIPHER_SUITE;
571 for (j = 0; j < datalen; j += 2) {
572 for (i = 0; i < x; i++) {
573 if (memcmp(ciphers[i].CipherSuite, &data[j], 2) ==
574 0) {
575 _gnutls_handshake_log("HSK: Selected cipher suite: ");
576 _gnutls_handshake_log("%s\n",
577 _gnutls_cipher_suite_get_name(*
578 ((GNUTLS_CipherSuite *) & data[j])));
579 memcpy(state->security_parameters.current_cipher_suite.CipherSuite, ciphers[i].CipherSuite, 2);
580 retval = 0;
581 goto finish;
586 finish:
587 gnutls_free(ciphers);
589 if (retval != 0) {
590 gnutls_assert();
591 return retval;
594 /* check if the credentials (username, public key etc. are ok)
596 if (_gnutls_get_kx_cred
597 (state->gnutls_key,
598 _gnutls_cipher_suite_get_kx_algo(state->security_parameters.
599 current_cipher_suite),
600 &err) == NULL && err != 0) {
601 gnutls_assert();
602 return GNUTLS_E_INSUFICIENT_CRED;
606 /* set the MOD_AUTH_STRUCT to the appropriate struct
607 * according to the KX algorithm. This is needed since all the
608 * handshake functions are read from there;
610 state->gnutls_internals.auth_struct =
611 _gnutls_kx_auth_struct(_gnutls_cipher_suite_get_kx_algo
612 (state->security_parameters.
613 current_cipher_suite));
614 if (state->gnutls_internals.auth_struct == NULL) {
616 _gnutls_handshake_log
617 ("HSK: Cannot find the appropriate handler for the KX algorithm\n");
618 gnutls_assert();
619 return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
622 return 0;
627 /* This selects the best supported compression method from the ones provided
629 int _gnutls_server_select_comp_method(GNUTLS_STATE state, opaque * data,
630 int datalen)
632 int x, i, j;
633 uint8 *ciphers;
635 x = _gnutls_supported_compression_methods(state, &ciphers);
636 memset( &state->gnutls_internals.compression_method, '\0', sizeof(CompressionMethod));
638 for (j = 0; j < datalen; j++) {
639 for (i = 0; i < x; i++) {
640 if (ciphers[i] == data[j]) {
641 state->gnutls_internals.compression_method =
642 _gnutls_compression_get_id(ciphers[i]);
643 gnutls_free(ciphers);
645 _gnutls_handshake_log("HSK: Selected Compression Method: %s\n",
646 gnutls_compression_get_name(state->gnutls_internals.
647 compression_method));
650 return 0;
655 /* we were not able to find a compatible compression
656 * algorithm
658 gnutls_free(ciphers);
659 gnutls_assert();
660 return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM;
664 /* This function sends an empty handshake packet. (like hello request).
665 * If the previous _gnutls_send_empty_handshake() returned
666 * GNUTLS_E_AGAIN or GNUTLS_E_INTERRUPTED, then it must be called again
667 * (until it returns ok), with NULL parameters.
669 int _gnutls_send_empty_handshake(GNUTLS_STATE state, HandshakeType type,
670 int again)
672 opaque data = 0;
673 opaque *ptr;
675 if (again == 0)
676 ptr = &data;
677 else
678 ptr = NULL;
680 return _gnutls_send_handshake(state, ptr, 0, type);
684 /* This function will hash the handshake message we sent.
686 static
687 int _gnutls_handshake_hash_add_sent( GNUTLS_STATE state, HandshakeType type,
688 opaque* dataptr, uint32 datalen) {
689 int ret;
691 if ( (ret=_gnutls_handshake_hash_pending( state)) < 0) {
692 gnutls_assert();
693 return ret;
696 if ( type != GNUTLS_HELLO_REQUEST) {
697 _gnutls_hash( state->gnutls_internals.handshake_mac_handle_sha, dataptr, datalen);
698 _gnutls_hash( state->gnutls_internals.handshake_mac_handle_md5, dataptr, datalen);
701 return 0;
705 /* This function sends a handshake message of type 'type' containing the
706 * data specified here. If the previous _gnutls_send_handshake() returned
707 * GNUTLS_E_AGAIN or GNUTLS_E_INTERRUPTED, then it must be called again
708 * (until it returns ok), with NULL parameters.
710 int _gnutls_send_handshake(GNUTLS_STATE state, void *i_data,
711 uint32 i_datasize, HandshakeType type)
713 int ret;
714 uint8 *data;
715 uint32 datasize;
716 int pos = 0;
718 if (i_data == NULL && i_datasize == 0) {
719 /* we are resuming a previously interrupted
720 * send.
722 ret = _gnutls_handshake_io_write_flush(state);
723 return ret;
727 if (i_data == NULL && i_datasize > 0) {
728 gnutls_assert();
729 return GNUTLS_E_INVALID_PARAMETERS;
732 /* first run */
733 datasize = i_datasize + HANDSHAKE_HEADER_SIZE;
734 data = gnutls_alloca(datasize);
735 if (data == NULL) {
736 gnutls_assert();
737 return GNUTLS_E_MEMORY_ERROR;
740 data[pos++] = (uint8) type;
741 _gnutls_write_uint24(i_datasize, &data[pos]);
742 pos += 3;
744 if (i_datasize > 0)
745 memcpy(&data[pos], i_data, i_datasize);
747 _gnutls_handshake_log("HSK: %s was send [%ld bytes]\n",
748 _gnutls_handshake2str(type), datasize);
751 /* Here we keep the handshake messages in order to hash them...
753 if ( type != GNUTLS_HELLO_REQUEST)
754 if ( (ret= _gnutls_handshake_hash_add_sent( state, type, data, datasize)) < 0) {
755 gnutls_assert();
756 gnutls_afree(data);
757 return ret;
760 ret =
761 _gnutls_handshake_io_send_int(state, GNUTLS_HANDSHAKE, type,
762 data, datasize);
764 gnutls_afree(data);
766 return ret;
769 /* This function will read the handshake header, and return it to the called. If the
770 * received handshake packet is not the one expected then it buffers the header, and
771 * returns UNEXPECTED_HANDSHAKE_PACKET.
773 * FIXME: This function is complex.
775 #define SSL2_HEADERS 1
776 static int _gnutls_recv_handshake_header(GNUTLS_STATE state,
777 HandshakeType type,
778 HandshakeType * recv_type)
780 int ret;
781 uint32 length32 = 0;
782 uint8 *dataptr = NULL; /* for realloc */
783 int handshake_header_size = HANDSHAKE_HEADER_SIZE;
785 /* if we have data into the buffer then return them, do not read the next packet.
786 * In order to return we need a full TLS handshake header, or in case of a version 2
787 * packet, then we return the first byte.
789 if (state->gnutls_internals.handshake_header_buffer.header_size ==
790 handshake_header_size || (state->gnutls_internals.v2_hello != 0
791 && type == GNUTLS_CLIENT_HELLO
792 && state->gnutls_internals.
793 handshake_header_buffer.
794 packet_length > 0)) {
796 *recv_type =
797 state->gnutls_internals.handshake_header_buffer.
798 recv_type;
800 return state->gnutls_internals.handshake_header_buffer.
801 packet_length;
804 /* Note: SSL2_HEADERS == 1 */
806 dataptr = state->gnutls_internals.handshake_header_buffer.header;
808 /* If we haven't already read the handshake headers.
810 if (state->gnutls_internals.handshake_header_buffer.header_size <
811 SSL2_HEADERS) {
812 ret =
813 _gnutls_handshake_io_recv_int(state, GNUTLS_HANDSHAKE,
814 type, dataptr,
815 SSL2_HEADERS);
817 if (ret < 0) {
818 gnutls_assert();
819 return (ret <
820 0) ? ret :
821 GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
824 if (ret != SSL2_HEADERS) {
825 gnutls_assert();
826 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
828 state->gnutls_internals.handshake_header_buffer.
829 header_size = SSL2_HEADERS;
832 if (state->gnutls_internals.v2_hello == 0
833 || type != GNUTLS_CLIENT_HELLO) {
834 ret =
835 _gnutls_handshake_io_recv_int(state, GNUTLS_HANDSHAKE,
836 type,
837 &dataptr[state->
838 gnutls_internals.
839 handshake_header_buffer.
840 header_size],
841 HANDSHAKE_HEADER_SIZE -
842 state->gnutls_internals.
843 handshake_header_buffer.
844 header_size);
845 if (ret <= 0) {
846 gnutls_assert();
847 return (ret <
848 0) ? ret :
849 GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
851 if (ret !=
852 HANDSHAKE_HEADER_SIZE -
853 state->gnutls_internals.handshake_header_buffer.
854 header_size) {
855 gnutls_assert();
856 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
858 *recv_type = dataptr[0];
860 /* we do not use DECR_LEN because we know
861 * that the packet has enough data.
863 length32 = _gnutls_read_uint24(&dataptr[1]);
864 handshake_header_size = HANDSHAKE_HEADER_SIZE;
866 _gnutls_handshake_log("HSK: %s was received [%ld bytes]\n",
867 _gnutls_handshake2str(dataptr[0]),
868 length32 + HANDSHAKE_HEADER_SIZE);
870 } else { /* v2 hello */
871 length32 = state->gnutls_internals.v2_hello - SSL2_HEADERS; /* we've read the first byte */
873 handshake_header_size = SSL2_HEADERS; /* we've already read one byte */
875 *recv_type = dataptr[0];
877 _gnutls_handshake_log("HSK: %s(v2) was received [%ld bytes]\n",
878 _gnutls_handshake2str(*recv_type),
879 length32 + handshake_header_size);
881 if (*recv_type != GNUTLS_CLIENT_HELLO) { /* it should be one or nothing */
882 gnutls_assert();
883 return GNUTLS_E_UNEXPECTED_HANDSHAKE_PACKET;
887 /* put the packet into the buffer */
888 state->gnutls_internals.handshake_header_buffer.header_size =
889 handshake_header_size;
890 state->gnutls_internals.handshake_header_buffer.packet_length =
891 length32;
892 state->gnutls_internals.handshake_header_buffer.recv_type =
893 *recv_type;
895 if (*recv_type != type) {
896 gnutls_assert();
897 return GNUTLS_E_UNEXPECTED_HANDSHAKE_PACKET;
900 return length32;
903 #define _gnutls_handshake_header_buffer_clear( state) state->gnutls_internals.handshake_header_buffer.header_size = 0
907 /* This function will hash the handshake headers and the
908 * handshake data.
910 static
911 int _gnutls_handshake_hash_add_recvd( GNUTLS_STATE state, HandshakeType recv_type,
912 opaque* header, uint16 header_size, opaque* dataptr, uint32 datalen) {
913 int ret;
915 /* The idea here is to hash the previous message we received,
916 * and add the one we just received into the handshake_hash_buffer.
919 if ( (ret=_gnutls_handshake_hash_pending( state)) < 0) {
920 gnutls_assert();
921 return ret;
924 /* here we buffer the handshake messages - needed at Finished message */
925 if ( recv_type != GNUTLS_HELLO_REQUEST) {
927 if ((ret =
928 _gnutls_handshake_buffer_put(state,
929 header, header_size)) < 0) {
930 gnutls_assert();
931 return ret;
934 if ( datalen > 0) {
935 if ((ret =
936 _gnutls_handshake_buffer_put(state, dataptr,
937 datalen)) < 0) {
938 gnutls_assert();
939 return ret;
944 return 0;
948 /* This function will receive handshake messages of the given types,
949 * and will pass the message to the right place in order to be processed.
950 * Eg. for the SERVER_HELLO message (if it is expected), it will be
951 * send to _gnutls_recv_hello().
953 int _gnutls_recv_handshake(GNUTLS_STATE state, uint8 ** data,
954 int *datalen, HandshakeType type,
955 Optional optional)
957 int ret;
958 uint32 length32 = 0;
959 opaque *dataptr = NULL;
960 HandshakeType recv_type;
962 ret = _gnutls_recv_handshake_header(state, type, &recv_type);
963 if (ret < 0) {
964 if (ret == GNUTLS_E_UNEXPECTED_HANDSHAKE_PACKET
965 && optional == OPTIONAL_PACKET) {
966 gnutls_assert();
967 *datalen = 0;
968 *data = NULL;
969 return 0; /* ok just ignore the packet */
971 gnutls_assert();
972 return ret;
976 length32 = ret;
978 if (length32 > 0)
979 dataptr = gnutls_malloc(length32);
980 else if (recv_type != GNUTLS_SERVER_HELLO_DONE) {
981 gnutls_assert();
982 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
985 if (dataptr == NULL && length32 > 0) {
986 gnutls_assert();
987 return GNUTLS_E_MEMORY_ERROR;
990 if (datalen != NULL)
991 *datalen = length32;
993 if (length32 > 0) {
994 ret =
995 _gnutls_handshake_io_recv_int(state, GNUTLS_HANDSHAKE,
996 type, dataptr, length32);
997 if (ret <= 0) {
998 gnutls_assert();
999 gnutls_free(dataptr);
1000 return (ret ==
1001 0) ? GNUTLS_E_UNEXPECTED_PACKET_LENGTH :
1002 ret;
1007 ret = GNUTLS_E_UNKNOWN_ERROR;
1009 if (data != NULL && length32 > 0)
1010 *data = dataptr;
1013 if ( (ret=_gnutls_handshake_hash_add_recvd( state, recv_type,
1014 state->gnutls_internals.handshake_header_buffer.header,
1015 state->gnutls_internals.handshake_header_buffer.header_size,
1016 dataptr, length32)) < 0) {
1017 gnutls_assert();
1018 _gnutls_handshake_header_buffer_clear(state);
1019 return ret;
1022 /* If we fail before this then we will reuse the handshake header
1023 * have have received above. if we get here the we clear the handshake
1024 * header we received.
1026 _gnutls_handshake_header_buffer_clear(state);
1028 switch (recv_type) {
1029 case GNUTLS_CLIENT_HELLO:
1030 case GNUTLS_SERVER_HELLO:
1031 ret = _gnutls_recv_hello(state, dataptr, length32);
1032 /* dataptr is freed because the caller does not
1033 * need it */
1034 gnutls_free(dataptr);
1035 *data = NULL;
1036 break;
1037 case GNUTLS_SERVER_HELLO_DONE:
1038 if (length32==0) ret = 0;
1039 else ret = GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
1040 break;
1041 case GNUTLS_CERTIFICATE_PKT:
1042 case GNUTLS_FINISHED:
1043 case GNUTLS_SERVER_KEY_EXCHANGE:
1044 case GNUTLS_CLIENT_KEY_EXCHANGE:
1045 case GNUTLS_CERTIFICATE_REQUEST:
1046 case GNUTLS_CERTIFICATE_VERIFY:
1047 ret = length32;
1048 break;
1049 default:
1050 gnutls_assert();
1051 gnutls_free(dataptr);
1052 *data = NULL;
1053 ret = GNUTLS_E_UNEXPECTED_HANDSHAKE_PACKET;
1056 return ret;
1059 /* This function checks if the given cipher suite is supported, and sets it
1060 * to the state;
1062 static int _gnutls_client_set_ciphersuite(GNUTLS_STATE state,
1063 opaque suite[2])
1065 uint8 z;
1066 GNUTLS_CipherSuite *cipher_suites;
1067 uint16 x;
1068 int i, err;
1070 z = 1;
1071 x = _gnutls_supported_ciphersuites(state, &cipher_suites);
1072 for (i = 0; i < x; i++) {
1073 if (memcmp(&cipher_suites[i], suite, 2) == 0) {
1074 z = 0;
1078 gnutls_free(cipher_suites);
1080 if (z != 0) {
1081 gnutls_assert();
1082 return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
1085 memcpy(state->security_parameters.
1086 current_cipher_suite.CipherSuite, suite, 2);
1088 _gnutls_handshake_log("HSK: Selected cipher suite: ");
1089 _gnutls_handshake_log("%s\n",
1090 _gnutls_cipher_suite_get_name(state->
1091 security_parameters.
1092 current_cipher_suite));
1095 /* check if the credentials (username, public key etc. are ok).
1096 * Actually checks if they exist.
1098 if (_gnutls_get_kx_cred
1099 (state->gnutls_key,
1100 _gnutls_cipher_suite_get_kx_algo(state->
1101 security_parameters.
1102 current_cipher_suite),
1103 &err) == NULL && err != 0) {
1104 gnutls_assert();
1105 return GNUTLS_E_INSUFICIENT_CRED;
1109 /* set the MOD_AUTH_STRUCT to the appropriate struct
1110 * according to the KX algorithm. This is needed since all the
1111 * handshake functions are read from there;
1113 state->gnutls_internals.auth_struct =
1114 _gnutls_kx_auth_struct(_gnutls_cipher_suite_get_kx_algo
1115 (state->security_parameters.
1116 current_cipher_suite));
1118 if (state->gnutls_internals.auth_struct == NULL) {
1120 _gnutls_handshake_log
1121 ("HSK: Cannot find the appropriate handler for the KX algorithm\n");
1122 gnutls_assert();
1123 return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
1127 return 0;
1130 /* This function sets the given comp method to the state.
1132 static int _gnutls_client_set_comp_method(GNUTLS_STATE state,
1133 opaque comp_method)
1135 uint8 z;
1136 uint8 *compression_methods;
1137 int i;
1139 z = _gnutls_supported_compression_methods(state,
1140 &compression_methods);
1141 for (i = 0; i < z; i++) {
1142 if (compression_methods[i] == comp_method) {
1143 z = 0;
1147 gnutls_free(compression_methods);
1149 if (z != 0) {
1150 gnutls_assert();
1151 return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM;
1154 state->gnutls_internals.compression_method =
1155 _gnutls_compression_get_id(comp_method);
1158 return 0;
1161 /* This function returns 0 if we are resuming a session or -1 otherwise.
1162 * This also sets the variables in the state. Used only while reading a server
1163 * hello.
1165 static int _gnutls_client_check_if_resuming(GNUTLS_STATE state,
1166 opaque * session_id,
1167 int session_id_len)
1170 _gnutls_handshake_log("HSK: SessionID length: %d\n", session_id_len);
1171 _gnutls_handshake_log("HSK: SessionID: %s\n",
1172 _gnutls_bin2hex(session_id, session_id_len));
1174 if ((state->gnutls_internals.resumed_security_parameters.
1175 session_id_size > 0)
1176 && memcmp(session_id,
1177 state->gnutls_internals.
1178 resumed_security_parameters.session_id,
1179 session_id_len) == 0) {
1180 /* resume session */
1181 memcpy(state->gnutls_internals.
1182 resumed_security_parameters.server_random,
1183 state->security_parameters.server_random,
1184 TLS_RANDOM_SIZE);
1185 memcpy(state->gnutls_internals.
1186 resumed_security_parameters.client_random,
1187 state->security_parameters.client_random,
1188 TLS_RANDOM_SIZE);
1189 state->gnutls_internals.resumed = RESUME_TRUE; /* we are resuming */
1191 return 0;
1192 } else {
1193 /* keep the new session id */
1194 state->gnutls_internals.resumed = RESUME_FALSE; /* we are not resuming */
1195 state->security_parameters.session_id_size =
1196 session_id_len;
1197 memcpy(state->security_parameters.session_id,
1198 session_id, session_id_len);
1200 return -1;
1205 /* This function read and parse the server hello handshake message.
1206 * This function also restores resumed parameters if we are resuming a
1207 * session.
1209 static int _gnutls_read_server_hello(GNUTLS_STATE state, char *data,
1210 int datalen)
1212 uint8 session_id_len = 0;
1213 int pos = 0;
1214 int ret = 0;
1215 GNUTLS_Version version;
1216 int len = datalen;
1218 if (datalen < 38) {
1219 gnutls_assert();
1220 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
1223 _gnutls_handshake_log("HSK: Server's version: %d.%d\n", data[pos], data[pos + 1]);
1225 DECR_LEN(len, 2);
1226 version = _gnutls_version_get(data[pos], data[pos + 1]);
1227 if (_gnutls_version_is_supported(state, version) == 0) {
1228 gnutls_assert();
1229 return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
1230 } else {
1231 _gnutls_set_current_version(state, version);
1234 pos += 2;
1236 DECR_LEN(len, TLS_RANDOM_SIZE);
1237 _gnutls_set_server_random(state, &data[pos]);
1238 pos += TLS_RANDOM_SIZE;
1241 /* Read session ID
1243 DECR_LEN(len, 1);
1244 session_id_len = data[pos++];
1246 if (len < session_id_len) {
1247 gnutls_assert();
1248 return GNUTLS_E_UNSUPPORTED_VERSION_PACKET;
1250 DECR_LEN(len, session_id_len);
1253 /* check if we are resuming and set the appropriate
1254 * values;
1256 if (_gnutls_client_check_if_resuming
1257 (state, &data[pos], session_id_len) == 0)
1258 return 0;
1259 pos += session_id_len;
1262 /* Check if the given cipher suite is supported and copy
1263 * it to the state.
1266 DECR_LEN(len, 2);
1267 ret = _gnutls_client_set_ciphersuite(state, &data[pos]);
1268 if (ret < 0) {
1269 gnutls_assert();
1270 return ret;
1272 pos += 2;
1276 /* move to compression
1278 DECR_LEN(len, 1);
1280 ret = _gnutls_client_set_comp_method(state, data[pos++]);
1281 if (ret < 0) {
1282 gnutls_assert();
1283 return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM;
1286 /* Parse extensions.
1288 if (version >= GNUTLS_TLS1) {
1289 ret = _gnutls_parse_extensions(state, &data[pos], len); /* len is the rest of the parsed length */
1290 if (ret < 0) {
1291 gnutls_assert();
1292 return ret;
1295 return ret;
1298 /* This function copies the appropriate ciphersuites, to a localy allocated buffer
1299 * Needed in client hello messages. Returns the new data length.
1301 static int _gnutls_copy_ciphersuites(GNUTLS_STATE state,
1302 opaque ** ret_data)
1304 int ret, i;
1305 GNUTLS_CipherSuite *cipher_suites;
1306 uint16 x;
1307 int datalen, pos;
1309 ret = _gnutls_supported_ciphersuites_sorted(state, &cipher_suites);
1310 if (ret <= 0) {
1311 gnutls_assert();
1312 if (ret==0) return GNUTLS_E_INVALID_REQUEST;
1313 else return ret;
1316 /* Here we remove any ciphersuite that does not conform
1317 * the certificate requested, or to the
1318 * authentication requested (eg SRP).
1320 ret =
1321 _gnutls_remove_unwanted_ciphersuites(state, &cipher_suites,
1322 ret, -1);
1323 if (ret < 0) {
1324 gnutls_assert();
1325 return ret;
1327 if (ret==0) {
1328 gnutls_assert();
1329 return GNUTLS_E_INSUFICIENT_CRED;
1333 x = ret;
1334 x *= sizeof(uint16); /* in order to get bytes */
1336 datalen = pos = 0;
1338 datalen += sizeof(uint16) + x;
1340 *ret_data = gnutls_malloc(datalen);
1343 if (*ret_data == NULL) {
1344 gnutls_assert();
1345 return GNUTLS_E_MEMORY_ERROR;
1349 _gnutls_write_uint16(x, *ret_data);
1350 pos += 2;
1352 for (i = 0; i < x / 2; i++) {
1353 memcpy(&(*ret_data)[pos], cipher_suites[i].CipherSuite, 2);
1354 pos += 2;
1356 gnutls_free(cipher_suites);
1358 return datalen;
1362 /* This function copies the appropriate compression methods, to a localy allocated buffer
1363 * Needed in hello messages. Returns the new data length.
1365 static int _gnutls_copy_comp_methods(GNUTLS_STATE state,
1366 opaque ** ret_data)
1368 int ret, i;
1369 uint8 *compression_methods, z;
1370 int datalen, pos;
1372 ret =
1373 _gnutls_supported_compression_methods(state,
1374 &compression_methods);
1375 if (ret < 0) {
1376 gnutls_assert();
1377 return ret;
1380 z = ret;
1382 datalen = pos = 0;
1383 datalen += z + 1;
1385 *ret_data = gnutls_malloc(datalen);
1386 if (*ret_data == NULL) {
1387 gnutls_assert();
1388 return GNUTLS_E_MEMORY_ERROR;
1391 (*ret_data)[pos++] = z; /* put the number of compression methods */
1393 for (i = 0; i < z; i++) {
1394 (*ret_data)[pos++] = compression_methods[i];
1397 gnutls_free(compression_methods);
1399 return datalen;
1402 /* This function sends the client hello handshake message.
1404 static int _gnutls_send_client_hello(GNUTLS_STATE state, int again)
1406 opaque *data = NULL;
1407 opaque *extdata;
1408 int extdatalen;
1409 int pos = 0;
1410 int datalen, ret = 0;
1411 opaque random[TLS_RANDOM_SIZE];
1412 GNUTLS_Version hver;
1414 opaque *SessionID =
1415 state->gnutls_internals.resumed_security_parameters.session_id;
1416 uint8 session_id_len =
1417 state->gnutls_internals.resumed_security_parameters.
1418 session_id_size;
1420 if (SessionID == NULL || session_id_len == 0) {
1421 session_id_len = 0;
1422 SessionID = NULL;
1425 data = NULL;
1426 datalen = 0;
1427 if (again == 0) {
1429 datalen = 2 + (session_id_len + 1) + TLS_RANDOM_SIZE;
1430 /* 2 for version, (4 for unix time + 28 for random bytes==TLS_RANDOM_SIZE)
1433 data = gnutls_malloc(datalen + 16); /* 16 is added to avoid realloc
1434 * if no much data are added.
1436 if (data == NULL) {
1437 gnutls_assert();
1438 return GNUTLS_E_MEMORY_ERROR;
1441 /* if we are resuming a session then we set the
1442 * version number to the previously established.
1444 if (SessionID == NULL)
1445 hver = _gnutls_version_max(state);
1446 else { /* we are resuming a session */
1447 hver =
1448 state->gnutls_internals.
1449 resumed_security_parameters.version;
1452 if (hver <= 0) {
1453 if (hver == 0)
1454 hver = GNUTLS_E_UNKNOWN_ERROR;
1455 gnutls_assert();
1456 return hver;
1459 data[pos++] = _gnutls_version_get_major(hver);
1460 data[pos++] = _gnutls_version_get_minor(hver);
1462 /* Set the version we advertized as maximum
1463 * (RSA uses it).
1465 _gnutls_set_adv_version( state, hver);
1467 /* Some implementations do not interoperate if we send a
1468 * different version in the record layer.
1469 * It seems they prefer to read the record's version
1470 * as the one we actually requested.
1471 * The proper behaviour is to use the one in the client hello
1472 * handshake packet and ignore the one in the packet's record
1473 * header.
1475 if (state->gnutls_internals.default_record_version==0)
1476 _gnutls_set_current_version(state, hver);
1477 else _gnutls_set_current_version(state,
1478 state->gnutls_internals.default_record_version);
1480 /* In order to know when this session was initiated.
1482 state->security_parameters.timestamp = time(NULL);
1484 /* Generate random data
1486 _gnutls_create_random(random);
1487 _gnutls_set_client_random(state, random);
1489 memcpy(&data[pos], random, TLS_RANDOM_SIZE);
1490 pos += TLS_RANDOM_SIZE;
1492 /* Copy the Session ID
1494 data[pos++] = session_id_len;
1496 if (session_id_len > 0) {
1497 memcpy(&data[pos], SessionID, session_id_len);
1499 pos += session_id_len;
1502 /* Copy the ciphersuites.
1504 extdatalen = _gnutls_copy_ciphersuites(state, &extdata);
1505 if (extdatalen > 0) {
1506 datalen += extdatalen;
1507 data = gnutls_realloc(data, datalen);
1508 if (data == NULL) {
1509 gnutls_assert();
1510 gnutls_free(extdata);
1511 return GNUTLS_E_MEMORY_ERROR;
1514 memcpy(&data[pos], extdata, extdatalen);
1515 gnutls_free(extdata);
1516 pos += extdatalen;
1518 } else {
1519 if (extdatalen == 0)
1520 extdatalen = GNUTLS_E_UNKNOWN_ERROR;
1521 gnutls_free(data);
1522 gnutls_assert();
1523 return extdatalen;
1527 /* Copy the compression methods.
1529 extdatalen = _gnutls_copy_comp_methods(state, &extdata);
1530 if (extdatalen > 0) {
1531 datalen += extdatalen;
1532 data = gnutls_realloc(data, datalen);
1533 if (data == NULL) {
1534 gnutls_assert();
1535 gnutls_free(extdata);
1536 return GNUTLS_E_MEMORY_ERROR;
1539 memcpy(&data[pos], extdata, extdatalen);
1540 gnutls_free(extdata);
1541 pos += extdatalen;
1543 } else {
1544 if (extdatalen == 0)
1545 extdatalen = GNUTLS_E_UNKNOWN_ERROR;
1546 gnutls_free(data);
1547 gnutls_assert();
1548 return extdatalen;
1551 /* Generate and copy TLS extensions.
1553 if (hver >= GNUTLS_TLS1) {
1554 extdatalen = _gnutls_gen_extensions(state, &extdata);
1555 if (extdatalen > 0) {
1556 datalen += extdatalen;
1557 data = gnutls_realloc(data, datalen);
1558 if (data == NULL) {
1559 gnutls_assert();
1560 gnutls_free(extdata);
1561 return GNUTLS_E_MEMORY_ERROR;
1564 memcpy(&data[pos], extdata, extdatalen);
1565 gnutls_free(extdata);
1570 ret =
1571 _gnutls_send_handshake(state, data, datalen,
1572 GNUTLS_CLIENT_HELLO);
1573 gnutls_free(data);
1575 return ret;
1578 static int _gnutls_send_server_hello(GNUTLS_STATE state, int again)
1580 opaque *data;
1581 opaque *extdata;
1582 int extdatalen;
1583 int pos = 0;
1584 int datalen, ret = 0;
1585 uint8 comp;
1586 opaque *SessionID = state->security_parameters.session_id;
1587 uint8 session_id_len = state->security_parameters.session_id_size;
1589 if (SessionID == NULL)
1590 session_id_len = 0;
1592 data = NULL;
1593 datalen = 0;
1595 if (again == 0) {
1596 datalen = 2 + session_id_len + 1 + TLS_RANDOM_SIZE + 3;
1597 extdatalen = _gnutls_gen_extensions(state, &extdata);
1599 data = gnutls_alloca(datalen + extdatalen);
1600 if (data == NULL) {
1601 gnutls_assert();
1602 gnutls_free(extdata);
1603 return GNUTLS_E_MEMORY_ERROR;
1606 data[pos++] =
1607 _gnutls_version_get_major(state->security_parameters.
1608 version);
1609 data[pos++] =
1610 _gnutls_version_get_minor(state->security_parameters.
1611 version);
1613 memcpy(&data[pos],
1614 state->security_parameters.server_random,
1615 TLS_RANDOM_SIZE);
1616 pos += TLS_RANDOM_SIZE;
1618 data[pos++] = session_id_len;
1619 if (session_id_len > 0) {
1620 memcpy(&data[pos], SessionID, session_id_len);
1622 pos += session_id_len;
1624 _gnutls_handshake_log("HSK: SessionID: %s\n",
1625 _gnutls_bin2hex(SessionID, session_id_len));
1627 memcpy(&data[pos],
1628 state->security_parameters.
1629 current_cipher_suite.CipherSuite, 2);
1630 pos += 2;
1632 comp =
1633 (uint8) _gnutls_compression_get_num(state->
1634 gnutls_internals.
1635 compression_method);
1636 data[pos++] = comp;
1639 if (extdatalen > 0) {
1640 datalen += extdatalen;
1642 memcpy(&data[pos], extdata, extdatalen);
1643 gnutls_free(extdata);
1647 ret =
1648 _gnutls_send_handshake(state, data, datalen,
1649 GNUTLS_SERVER_HELLO);
1650 gnutls_afree(data);
1652 return ret;
1655 int _gnutls_send_hello(GNUTLS_STATE state, int again)
1657 int ret;
1659 if (state->security_parameters.entity == GNUTLS_CLIENT) {
1660 ret = _gnutls_send_client_hello(state, again);
1662 } else { /* SERVER */
1663 ret = _gnutls_send_server_hello(state, again);
1666 return ret;
1669 /* RECEIVE A HELLO MESSAGE. This should be called from gnutls_recv_handshake_int only if a
1670 * hello message is expected. It uses the security_parameters.current_cipher_suite
1671 * and gnutls_internals.compression_method.
1673 int _gnutls_recv_hello(GNUTLS_STATE state, char *data, int datalen)
1675 int ret;
1677 if (state->security_parameters.entity == GNUTLS_CLIENT) {
1678 ret = _gnutls_read_server_hello(state, data, datalen);
1679 if (ret < 0) {
1680 gnutls_assert();
1681 return ret;
1683 } else { /* Server side reading a client hello */
1685 ret = _gnutls_read_client_hello(state, data, datalen);
1686 if (ret < 0) {
1687 gnutls_assert();
1688 return ret;
1692 return ret;
1695 /* The packets in gnutls_handshake (it's more broad than original TLS handshake)
1697 * Client Server
1699 * ClientHello -------->
1700 * <-------- ServerHello
1702 * Certificate*
1703 * ServerKeyExchange*
1704 * Client Key Exchange0 -------->
1705 * <-------- CertificateRequest*
1707 * <-------- Server Key Exchange2
1708 * <-------- ServerHelloDone
1709 * Certificate*
1710 * ClientKeyExchange
1711 * CertificateVerify*
1712 * [ChangeCipherSpec]
1713 * Finished -------->
1714 * [ChangeCipherSpec]
1715 * <-------- Finished
1717 * (*): means optional packet.
1721 * gnutls_rehandshake - This function will renegotiate security parameters
1722 * @state: is a a &GNUTLS_STATE structure.
1724 * This function will renegotiate security parameters with the
1725 * client. This should only be called in case of a server.
1727 * This message informs the peer that we want to renegotiate
1728 * parameters (perform a handshake).
1730 * If this function succeeds (returns 0), you must call
1731 * the gnutls_handshake() function in order to negotiate
1732 * the new parameters.
1734 * If the client does not wish to renegotiate parameters he
1735 * will reply with an alert message, thus the return code will be
1736 * GNUTLS_E_WARNING_ALERT_RECEIVED and the alert will be
1737 * GNUTLS_A_NO_RENEGOTIATION.
1739 int gnutls_rehandshake(GNUTLS_STATE state)
1741 int ret;
1743 /* only server sends that handshake packet */
1744 if (state->security_parameters.entity == GNUTLS_CLIENT)
1745 return GNUTLS_E_INVALID_REQUEST;
1747 ret =
1748 _gnutls_send_empty_handshake(state, GNUTLS_HELLO_REQUEST,
1749 AGAIN(STATE50));
1750 STATE = STATE50;
1752 if (ret < 0) {
1753 gnutls_assert();
1754 return ret;
1756 STATE = STATE0;
1758 return 0;
1761 static int _gnutls_abort_handshake( GNUTLS_STATE state, int ret) {
1762 if ( ((ret==GNUTLS_E_WARNING_ALERT_RECEIVED) &&
1763 ( gnutls_alert_get(state) == GNUTLS_A_NO_RENEGOTIATION))
1764 || ret==GNUTLS_E_GOT_APPLICATION_DATA)
1765 return 0;
1767 /* this doesn't matter */
1768 return GNUTLS_E_UNKNOWN_ERROR;
1772 /* This function initialized the handshake hash state.
1773 * required for finished messages.
1775 inline
1776 static int _gnutls_handshake_hash_init( GNUTLS_STATE state) {
1778 if ( state->gnutls_internals.handshake_mac_handle_md5==NULL) {
1779 state->gnutls_internals.handshake_mac_handle_md5 = _gnutls_hash_init( GNUTLS_MAC_MD5);
1781 if (state->gnutls_internals.handshake_mac_handle_md5==GNUTLS_HASH_FAILED) {
1782 gnutls_assert();
1783 return GNUTLS_E_MEMORY_ERROR;
1787 if ( state->gnutls_internals.handshake_mac_handle_sha==NULL) {
1788 state->gnutls_internals.handshake_mac_handle_sha = _gnutls_hash_init( GNUTLS_MAC_SHA);
1789 if (state->gnutls_internals.handshake_mac_handle_sha==GNUTLS_HASH_FAILED) {
1790 gnutls_assert();
1791 return GNUTLS_E_MEMORY_ERROR;
1795 return 0;
1799 * gnutls_handshake - This the main function in the handshake protocol.
1800 * @state: is a a &GNUTLS_STATE structure.
1802 * This function does the handshake of the TLS/SSL protocol,
1803 * and initializes the TLS connection.
1805 * This function will fail if any problem is encountered,
1806 * and will return a negative error code. In case of a client,
1807 * if it has been asked to resume a session, but the server didn't, then
1808 * a full handshake will be performed.
1810 * This function may also return the non-fatal errors GNUTLS_E_AGAIN, or
1811 * GNUTLS_E_INTERRUPTED. In that case you may resume the handshake
1812 * (call this function again, until it returns ok)
1814 * If this function is called by a server after a rehandshake request then
1815 * GNUTLS_E_GOT_APPLICATION_DATA or GNUTLS_E_WARNING_ALERT_RECEIVED
1816 * may be returned. Note that these are non fatal errors, only in the
1817 * case of a rehandshake. In that case they mean that the client
1818 * rejected the rehandshake request.
1821 int gnutls_handshake(GNUTLS_STATE state)
1823 int ret;
1825 if ( (ret=_gnutls_handshake_hash_init( state)) < 0) {
1826 gnutls_assert();
1827 return ret;
1830 if (state->security_parameters.entity == GNUTLS_CLIENT) {
1831 ret = gnutls_handshake_client(state);
1832 } else {
1833 ret = gnutls_handshake_server(state);
1835 if (ret < 0) {
1836 /* In the case of a rehandshake abort
1837 * we should reset the handshake's state
1839 if (_gnutls_abort_handshake( state, ret) == 0)
1840 STATE = STATE0;
1841 return ret;
1844 ret = gnutls_handshake_common(state);
1846 if (ret < 0) {
1847 if (_gnutls_abort_handshake( state, ret) == 0)
1848 STATE = STATE0;
1849 return ret;
1852 STATE = STATE0;
1854 _gnutls_handshake_io_buffer_clear(state);
1855 _gnutls_handshake_internal_state_clear(state);
1857 return 0;
1860 #define IMED_RET( str, ret) \
1861 if (ret < 0) { \
1862 if (gnutls_error_is_fatal(ret)==0) return ret; \
1863 gnutls_assert(); \
1864 ERR( str, ret); \
1865 _gnutls_handshake_hash_buffers_clear(state); \
1866 return ret; \
1872 * gnutls_handshake_client
1873 * This function performs the client side of the handshake of the TLS/SSL protocol.
1875 int gnutls_handshake_client(GNUTLS_STATE state)
1877 int ret = 0;
1879 #ifdef HANDSHAKE_DEBUG
1880 if (state->gnutls_internals.resumed_security_parameters.
1881 session_id_size > 0)
1882 _gnutls_handshake_log("HSK: Ask to resume: %s\n",
1883 _gnutls_bin2hex(state->gnutls_internals.
1884 resumed_security_parameters.
1885 session_id,
1886 state->gnutls_internals.
1887 resumed_security_parameters.
1888 session_id_size));
1889 #endif
1891 switch (STATE) {
1892 case STATE0:
1893 case STATE1:
1894 ret = _gnutls_send_hello(state, AGAIN(STATE1));
1895 STATE = STATE1;
1896 IMED_RET("send hello", ret);
1898 case STATE2:
1899 /* receive the server hello */
1900 ret =
1901 _gnutls_recv_handshake(state, NULL, NULL,
1902 GNUTLS_SERVER_HELLO,
1903 MANDATORY_PACKET);
1904 STATE = STATE2;
1905 IMED_RET("recv hello", ret);
1907 case STATE3:
1908 /* RECV CERTIFICATE */
1909 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1910 ret = _gnutls_recv_server_certificate(state);
1911 STATE = STATE3;
1912 IMED_RET("recv server certificate", ret);
1914 case STATE4:
1915 /* receive the server key exchange */
1916 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1917 ret = _gnutls_recv_server_kx_message(state);
1918 STATE = STATE4;
1919 IMED_RET("recv server kx message", ret);
1921 case STATE5:
1922 /* Added for SRP,
1923 * send the client key exchange for SRP
1925 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1926 ret =
1927 _gnutls_send_client_kx_message0(state,
1928 AGAIN(STATE5));
1929 STATE = STATE5;
1930 IMED_RET("send client kx0", ret);
1932 case STATE6:
1933 /* receive the server certificate request - if any
1936 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1937 ret =
1938 _gnutls_recv_server_certificate_request(state);
1939 STATE = STATE6;
1940 IMED_RET("recv server certificate request message", ret);
1942 case STATE7:
1943 /* receive the server key exchange (B) (SRP only)
1946 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1947 ret = _gnutls_recv_server_kx_message2(state);
1948 STATE = STATE7;
1949 IMED_RET("recv server kx message2", ret);
1951 case STATE8:
1952 /* receive the server hello done */
1953 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1954 ret =
1955 _gnutls_recv_handshake(state, NULL, NULL,
1956 GNUTLS_SERVER_HELLO_DONE,
1957 MANDATORY_PACKET);
1958 STATE = STATE8;
1959 IMED_RET("recv server hello done", ret);
1961 case STATE9:
1962 /* send our certificate - if any and if requested
1964 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1965 ret =
1966 _gnutls_send_client_certificate(state,
1967 AGAIN(STATE9));
1968 STATE = STATE9;
1969 IMED_RET("send client certificate", ret);
1971 case STATE10:
1972 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1973 ret =
1974 _gnutls_send_client_kx_message(state,
1975 AGAIN(STATE10));
1976 STATE = STATE10;
1977 IMED_RET("send client kx", ret);
1979 case STATE11:
1980 /* send client certificate verify */
1981 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
1982 ret =
1983 _gnutls_send_client_certificate_verify(state,
1984 AGAIN
1985 (STATE11));
1986 STATE = STATE11;
1987 IMED_RET("send client certificate verify", ret);
1989 STATE = STATE0;
1993 return 0;
1996 /* This function sends the final handshake packets and initializes connection
1998 static int _gnutls_send_handshake_final(GNUTLS_STATE state, int init)
2000 int ret = 0;
2002 /* Send the CHANGE CIPHER SPEC PACKET */
2004 switch (STATE) {
2005 case STATE0:
2006 case STATE20:
2007 ret =
2008 _gnutls_send_change_cipher_spec(state, AGAIN(STATE20));
2009 STATE = STATE20;
2010 if (ret < 0) {
2011 ERR("send ChangeCipherSpec", ret);
2012 gnutls_assert();
2013 return ret;
2016 /* Initialize the connection state (start encryption) - in case of client
2018 if (init == TRUE) {
2019 ret = _gnutls_connection_state_init(state);
2020 if (ret < 0) {
2021 gnutls_assert();
2022 return ret;
2026 ret = _gnutls_write_connection_state_init(state);
2027 if (ret < 0) {
2028 gnutls_assert();
2029 return ret;
2032 case STATE21:
2033 /* send the finished message */
2034 ret = _gnutls_send_finished(state, AGAIN(STATE21));
2035 STATE = STATE21;
2036 if (ret < 0) {
2037 ERR("send Finished", ret);
2038 gnutls_assert();
2039 return ret;
2042 STATE = STATE0;
2045 return 0;
2048 /* This function receives the final handshake packets
2049 * And executes the appropriate function to initialize the
2050 * read state.
2052 static int _gnutls_recv_handshake_final(GNUTLS_STATE state, int init)
2054 int ret = 0;
2055 uint8 ch;
2057 switch (STATE) {
2058 case STATE0:
2059 case STATE30:
2060 ret =
2061 gnutls_recv_int(state, GNUTLS_CHANGE_CIPHER_SPEC, -1,
2062 &ch, 1);
2063 STATE = STATE30;
2064 if (ret <= 0) {
2065 ERR("recv ChangeCipherSpec", ret);
2066 gnutls_assert();
2067 return (ret <
2068 0) ? ret :
2069 GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
2072 /* Initialize the connection state (start encryption) - in case of server */
2073 if (init == TRUE) {
2074 ret = _gnutls_connection_state_init(state);
2075 if (ret < 0) {
2076 gnutls_assert();
2077 return ret;
2081 ret = _gnutls_read_connection_state_init(state);
2082 if (ret < 0) {
2083 gnutls_assert();
2084 return ret;
2087 case STATE31:
2088 ret = _gnutls_recv_finished(state);
2089 STATE = STATE31;
2090 if (ret < 0) {
2091 ERR("recv finished", ret);
2092 gnutls_assert();
2093 return ret;
2095 STATE = STATE0;
2099 return 0;
2103 * gnutls_handshake_server
2104 * This function does the server stuff of the handshake protocol.
2107 int gnutls_handshake_server(GNUTLS_STATE state)
2109 int ret = 0;
2111 switch (STATE) {
2112 case STATE0:
2113 case STATE1:
2114 ret =
2115 _gnutls_recv_handshake(state, NULL, NULL,
2116 GNUTLS_CLIENT_HELLO,
2117 MANDATORY_PACKET);
2118 STATE = STATE1;
2119 IMED_RET("recv hello", ret);
2121 case STATE2:
2122 ret = _gnutls_send_hello(state, AGAIN(STATE2));
2123 STATE = STATE2;
2124 IMED_RET("send hello", ret);
2126 /* SEND CERTIFICATE + KEYEXCHANGE + CERTIFICATE_REQUEST */
2127 case STATE3:
2128 /* NOTE: these should not be send if we are resuming */
2130 if (state->gnutls_internals.resumed == RESUME_FALSE)
2131 ret =
2132 _gnutls_send_server_certificate(state,
2133 AGAIN(STATE3));
2134 STATE = STATE3;
2135 IMED_RET("send server certificate", ret);
2137 case STATE4:
2138 /* send server key exchange (A) */
2139 if (state->gnutls_internals.resumed == RESUME_FALSE)
2140 ret =
2141 _gnutls_send_server_kx_message(state,
2142 AGAIN(STATE4));
2143 STATE = STATE4;
2144 IMED_RET("send server kx", ret);
2146 case STATE5:
2147 /* Send certificate request - if requested to */
2148 if (state->gnutls_internals.resumed == RESUME_FALSE)
2149 ret =
2150 _gnutls_send_server_certificate_request(state,
2151 AGAIN
2152 (STATE5));
2153 STATE = STATE5;
2154 IMED_RET("send server cert request", ret);
2156 case STATE6:
2157 /* Added for SRP which uses a different handshake */
2158 /* receive the client key exchange message */
2160 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
2161 ret = _gnutls_recv_client_kx_message0(state);
2162 STATE = STATE6;
2163 IMED_RET("recv client kx0", ret);
2165 case STATE7:
2166 /* send server key exchange (B) */
2167 if (state->gnutls_internals.resumed == RESUME_FALSE)
2168 ret =
2169 _gnutls_send_server_kx_message2(state,
2170 AGAIN(STATE7));
2171 STATE = STATE7;
2172 IMED_RET("send server kx2", ret);
2174 case STATE8:
2175 /* send the server hello done */
2176 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
2177 ret =
2178 _gnutls_send_empty_handshake(state,
2179 GNUTLS_SERVER_HELLO_DONE,
2180 AGAIN(STATE8));
2181 STATE = STATE8;
2182 IMED_RET("send server hello done", ret);
2185 /* RECV CERTIFICATE + KEYEXCHANGE + CERTIFICATE_VERIFY */
2186 case STATE9:
2187 /* receive the client certificate message */
2188 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
2189 ret = _gnutls_recv_client_certificate(state);
2190 STATE = STATE9;
2191 IMED_RET("recv client certificate", ret);
2193 case STATE10:
2194 /* receive the client key exchange message */
2195 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
2196 ret = _gnutls_recv_client_kx_message(state);
2197 STATE = STATE10;
2198 IMED_RET("recv client kx", ret);
2200 case STATE11:
2201 /* receive the client certificate verify message */
2202 if (state->gnutls_internals.resumed == RESUME_FALSE) /* if we are not resuming */
2203 ret =
2204 _gnutls_recv_client_certificate_verify_message
2205 (state);
2206 STATE = STATE11;
2207 IMED_RET("recv client certificate verify", ret);
2209 STATE = STATE0; /* finished thus clear state */
2212 return 0;
2215 int gnutls_handshake_common(GNUTLS_STATE state)
2217 int ret = 0;
2220 /* send and recv the change cipher spec and finished messages */
2221 if ((state->gnutls_internals.resumed == RESUME_TRUE
2222 && state->security_parameters.entity == GNUTLS_CLIENT)
2223 || (state->gnutls_internals.resumed == RESUME_FALSE
2224 && state->security_parameters.entity == GNUTLS_SERVER)) {
2225 /* if we are a client resuming - or we are a server not resuming */
2227 ret = _gnutls_recv_handshake_final(state, TRUE);
2228 IMED_RET("recv handshake final", ret);
2230 ret = _gnutls_send_handshake_final(state, FALSE);
2231 IMED_RET("send handshake final", ret);
2232 } else { /* if we are a client not resuming - or we are a server resuming */
2234 ret = _gnutls_send_handshake_final(state, TRUE);
2235 IMED_RET("send handshake final 2", ret);
2237 ret = _gnutls_recv_handshake_final(state, FALSE);
2238 IMED_RET("recv handshake final 2", ret);
2241 if (state->security_parameters.entity == GNUTLS_SERVER) {
2242 /* in order to support session resuming */
2243 _gnutls_server_register_current_session(state);
2246 /* clear handshake buffer */
2247 _gnutls_handshake_hash_buffers_clear(state);
2248 return ret;
2252 int _gnutls_generate_session_id(char *session_id, uint8 * len)
2254 opaque rand[TLS_RANDOM_SIZE];
2255 if (_gnutls_get_random(rand, TLS_RANDOM_SIZE, GNUTLS_WEAK_RANDOM) <
2256 0) {
2257 gnutls_assert();
2258 return GNUTLS_E_MEMORY_ERROR;
2260 memcpy(session_id, rand, TLS_RANDOM_SIZE);
2261 *len = TLS_RANDOM_SIZE;
2263 _gnutls_handshake_log("HSK: Generated SessionID: %s\n",
2264 _gnutls_bin2hex(session_id, TLS_RANDOM_SIZE));
2266 return 0;
2269 int _gnutls_recv_hello_request(GNUTLS_STATE state, void *data,
2270 uint32 data_size)
2272 uint8 type;
2274 if (state->security_parameters.entity == GNUTLS_SERVER) {
2275 gnutls_assert();
2276 return GNUTLS_E_UNEXPECTED_PACKET;
2278 if (data_size < 1) {
2279 gnutls_assert();
2280 return GNUTLS_E_UNEXPECTED_PACKET_LENGTH;
2282 type = ((uint8 *) data)[0];
2283 if (type == GNUTLS_HELLO_REQUEST)
2284 return GNUTLS_E_REHANDSHAKE;
2285 else {
2286 gnutls_assert();
2287 return GNUTLS_E_UNEXPECTED_PACKET;
2291 /* This function will remove algorithms that are not supported by
2292 * the requested authentication method. We remove algorithm if
2293 * we have a certificate with keyUsage bits set.
2295 * This does a more high level check than gnutls_supported_ciphersuites(),
2296 * by checking certificates etc.
2298 int _gnutls_remove_unwanted_ciphersuites(GNUTLS_STATE state,
2299 GNUTLS_CipherSuite **
2300 cipherSuites, int numCipherSuites,
2301 PKAlgorithm requested_pk_algo)
2304 int ret = 0;
2305 GNUTLS_CipherSuite *newSuite;
2306 int newSuiteSize = 0, i, j, keep;
2307 const GNUTLS_CERTIFICATE_CREDENTIALS x509_cred;
2308 const gnutls_cert *cert = NULL;
2309 KXAlgorithm *alg;
2310 int alg_size;
2311 KXAlgorithm kx;
2314 /* if we should use a specific certificate,
2315 * we should remove all algorithms that are not supported
2316 * by that certificate and are on the same authentication
2317 * method (CERTIFICATE).
2320 x509_cred =
2321 _gnutls_get_cred(state->gnutls_key, GNUTLS_CRD_CERTIFICATE, NULL);
2323 /* if x509_cred==NULL we should remove all X509 ciphersuites
2326 cert = NULL;
2327 if (state->security_parameters.entity == GNUTLS_SERVER)
2328 cert = _gnutls_server_find_cert(state, requested_pk_algo);
2330 if (cert == NULL) {
2331 /* No certificate was found
2333 gnutls_assert();
2334 alg_size = 0;
2335 alg = NULL;
2336 } else {
2337 /* get all the key exchange algorithms that are
2338 * supported by the X509 certificate parameters.
2340 if ((ret =
2341 _gnutls_cert_supported_kx(cert, &alg,
2342 &alg_size)) < 0) {
2343 gnutls_assert();
2344 return ret;
2348 newSuite =
2349 gnutls_malloc(numCipherSuites * sizeof(GNUTLS_CipherSuite));
2350 if (newSuite == NULL) {
2351 gnutls_assert();
2352 gnutls_free(alg);
2353 return GNUTLS_E_MEMORY_ERROR;
2356 /* now removes ciphersuites based on the KX algorithm
2358 for (i = 0; i < numCipherSuites; i++) {
2359 /* finds the key exchange algorithm in
2360 * the ciphersuite
2362 kx = _gnutls_cipher_suite_get_kx_algo((*cipherSuites)[i]);
2364 keep = 0;
2366 /* if it is defined but had no credentials
2368 if (_gnutls_get_kx_cred
2369 (state->gnutls_key, kx, NULL) == NULL) {
2370 keep = 1;
2371 } else
2372 /* If there was no credentials to use with the specified
2373 * key exchange method, then just remove it.
2375 if (_gnutls_map_kx_get_cred(kx) == GNUTLS_CRD_CERTIFICATE) {
2376 keep = 1; /* do not keep */
2377 if (x509_cred != NULL) {
2378 if (state->security_parameters.entity ==
2379 GNUTLS_SERVER) {
2380 /* here we check if the KX algorithm
2381 * is compatible with the certificate.
2383 for (j = 0; j < alg_size; j++) {
2384 if (alg[j] == kx) {
2385 keep = 0;
2386 break;
2389 } else /* CLIENT */
2390 keep = 0;
2394 if (keep == 0) {
2396 _gnutls_handshake_log("HSK: Keeping ciphersuite: ");
2397 _gnutls_handshake_log("%s\n",
2398 _gnutls_cipher_suite_get_name(*
2399 ((GNUTLS_CipherSuite *) & (*cipherSuites)[i].CipherSuite)));
2401 memcpy(newSuite[newSuiteSize].CipherSuite,
2402 (*cipherSuites)[i].CipherSuite, 2);
2403 newSuiteSize++;
2404 } else {
2405 _gnutls_handshake_log("HSK: Removing ciphersuite: ");
2406 _gnutls_handshake_log("%s\n",
2407 _gnutls_cipher_suite_get_name(*
2408 ((GNUTLS_CipherSuite *) & (*cipherSuites)[i].CipherSuite)));
2413 gnutls_free(alg);
2414 gnutls_free(*cipherSuites);
2415 *cipherSuites = newSuite;
2417 ret = newSuiteSize;
2419 return ret;
2424 * gnutls_handshake_set_max_packet_length - This function will set the maximum length of a handshake message
2425 * @state: is a a &GNUTLS_STATE structure.
2426 * @max: is the maximum number.
2428 * This function will set the maximum size of a handshake message.
2429 * Handshake messages over this size are rejected.
2430 * The default value is 16kb which is large enough. Set this to 0 if you do not want
2431 * to set an upper limit.
2434 void gnutls_handshake_set_max_packet_length(GNUTLS_STATE state, int max)
2436 state->gnutls_internals.max_handshake_data_buffer_size = max;
2439 void _gnutls_set_adv_version( GNUTLS_STATE state, GNUTLS_Version ver) {
2440 set_adv_version( state, _gnutls_version_get_major(ver), _gnutls_version_get_minor(ver));
2443 GNUTLS_Version _gnutls_get_adv_version( GNUTLS_STATE state) {
2444 return _gnutls_version_get( _gnutls_get_adv_version_major( state),
2445 _gnutls_get_adv_version_minor( state));