Honor uninitialized private key in destructor
[gnutls.git] / lib / gnutls_sig.c
blob9a925c3eba4086890260d26b415215fac5a20ee0
1 /*
2 * Copyright (C) 2001, 2004, 2005, 2006, 2007, 2008, 2009, 2010 Free
3 * Software Foundation, Inc.
5 * Author: Nikos Mavrogiannopoulos
7 * This file is part of GnuTLS.
9 * The GnuTLS is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public License
11 * as published by the Free Software Foundation; either version 2.1 of
12 * the License, or (at your option) any later version.
14 * This library is distributed in the hope that it will be useful, but
15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * Lesser General Public License for more details.
19 * You should have received a copy of the GNU Lesser General Public
20 * License along with this library; if not, write to the Free Software
21 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
22 * USA
26 #include <gnutls_int.h>
27 #include <gnutls_errors.h>
28 #include <x509_b64.h>
29 #include <auth_cert.h>
30 #include <gnutls_algorithms.h>
31 #include <gnutls_cert.h>
32 #include <gnutls_datum.h>
33 #include <gnutls_mpi.h>
34 #include <gnutls_global.h>
35 #include <gnutls_pk.h>
36 #include <debug.h>
37 #include <gnutls_buffers.h>
38 #include <gnutls_sig.h>
39 #include <gnutls_kx.h>
40 #include <libtasn1.h>
41 #include <ext_signature.h>
42 #include <gnutls_state.h>
43 #include <x509/common.h>
45 static int
46 sign_tls_hash (gnutls_session_t session, gnutls_digest_algorithm_t hash_algo,
47 gnutls_cert * cert, gnutls_privkey_t pkey,
48 const gnutls_datum_t * hash_concat,
49 gnutls_datum_t * signature);
51 /* While this is currently equal to the length of RSA/SHA512
52 * signature, it should also be sufficient for DSS signature and any
53 * other RSA signatures including one with the old MD5/SHA1-combined
54 * format.
56 #define MAX_SIG_SIZE 19 + MAX_HASH_SIZE
58 /* Generates a signature of all the random data and the parameters.
59 * Used in DHE_* ciphersuites.
61 int
62 _gnutls_handshake_sign_data (gnutls_session_t session, gnutls_cert * cert,
63 gnutls_privkey_t pkey, gnutls_datum_t * params,
64 gnutls_datum_t * signature,
65 gnutls_sign_algorithm_t * sign_algo)
67 gnutls_datum_t dconcat;
68 int ret;
69 digest_hd_st td_sha;
70 opaque concat[MAX_SIG_SIZE];
71 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
72 gnutls_digest_algorithm_t hash_algo;
74 *sign_algo =
75 _gnutls_session_get_sign_algo (session, cert);
76 if (*sign_algo == GNUTLS_SIGN_UNKNOWN)
78 gnutls_assert ();
79 return GNUTLS_E_UNKNOWN_PK_ALGORITHM;
82 hash_algo = _gnutls_sign_get_hash_algorithm (*sign_algo);
84 _gnutls_handshake_log ("HSK[%p]: signing handshake data: using %s\n",
85 session, gnutls_sign_algorithm_get_name (*sign_algo));
87 ret = _gnutls_hash_init (&td_sha, hash_algo);
88 if (ret < 0)
90 gnutls_assert ();
91 return ret;
94 _gnutls_hash (&td_sha, session->security_parameters.client_random,
95 GNUTLS_RANDOM_SIZE);
96 _gnutls_hash (&td_sha, session->security_parameters.server_random,
97 GNUTLS_RANDOM_SIZE);
98 _gnutls_hash (&td_sha, params->data, params->size);
100 switch (cert->subject_pk_algorithm)
102 case GNUTLS_PK_RSA:
103 if (!_gnutls_version_has_selectable_sighash (ver))
105 digest_hd_st td_md5;
107 ret = _gnutls_hash_init (&td_md5, GNUTLS_MAC_MD5);
108 if (ret < 0)
110 gnutls_assert ();
111 return ret;
114 _gnutls_hash (&td_md5, session->security_parameters.client_random,
115 GNUTLS_RANDOM_SIZE);
116 _gnutls_hash (&td_md5, session->security_parameters.server_random,
117 GNUTLS_RANDOM_SIZE);
118 _gnutls_hash (&td_md5, params->data, params->size);
120 _gnutls_hash_deinit (&td_md5, concat);
121 _gnutls_hash_deinit (&td_sha, &concat[16]);
123 dconcat.data = concat;
124 dconcat.size = 36;
126 else
127 { /* TLS 1.2 way */
129 _gnutls_hash_deinit (&td_sha, concat);
131 dconcat.data = concat;
132 dconcat.size = _gnutls_hash_get_algo_len (hash_algo);
134 break;
135 case GNUTLS_PK_DSA:
136 _gnutls_hash_deinit (&td_sha, concat);
138 if ((hash_algo != GNUTLS_DIG_SHA1) && (hash_algo != GNUTLS_DIG_SHA224)
139 && (hash_algo != GNUTLS_DIG_SHA256))
141 gnutls_assert ();
142 return GNUTLS_E_INTERNAL_ERROR;
144 dconcat.data = concat;
145 dconcat.size = _gnutls_hash_get_algo_len (hash_algo);
146 break;
148 default:
149 gnutls_assert ();
150 _gnutls_hash_deinit (&td_sha, NULL);
151 return GNUTLS_E_INTERNAL_ERROR;
154 ret = sign_tls_hash (session, hash_algo, cert, pkey, &dconcat, signature);
155 if (ret < 0)
157 gnutls_assert ();
160 return ret;
165 /* This will create a PKCS1 or DSA signature, using the given parameters, and the
166 * given data. The output will be allocated and be put in signature.
169 _gnutls_soft_sign (gnutls_pk_algorithm_t algo, bigint_t * params,
170 int params_size, const gnutls_datum_t * data,
171 gnutls_datum_t * signature)
173 int ret;
175 switch (algo)
177 case GNUTLS_PK_RSA:
178 /* encrypt */
179 if ((ret = _gnutls_pkcs1_rsa_encrypt (signature, data, params,
180 params_size, 1)) < 0)
182 gnutls_assert ();
183 return ret;
186 break;
187 case GNUTLS_PK_DSA:
188 /* sign */
189 if ((ret = _gnutls_dsa_sign (signature, data, params, params_size)) < 0)
191 gnutls_assert ();
192 return ret;
194 break;
195 default:
196 gnutls_assert ();
197 return GNUTLS_E_INTERNAL_ERROR;
198 break;
201 return 0;
204 /* This will create a PKCS1 or DSA signature, as defined in the TLS protocol.
205 * Cert is the certificate of the corresponding private key. It is only checked if
206 * it supports signing.
208 static int
209 sign_tls_hash (gnutls_session_t session, gnutls_digest_algorithm_t hash_algo,
210 gnutls_cert * cert, gnutls_privkey_t pkey,
211 const gnutls_datum_t * hash_concat,
212 gnutls_datum_t * signature)
214 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
216 /* If our certificate supports signing
219 if (cert != NULL)
221 if (cert->key_usage != 0)
222 if (!(cert->key_usage & GNUTLS_KEY_DIGITAL_SIGNATURE))
224 gnutls_assert ();
225 return GNUTLS_E_KEY_USAGE_VIOLATION;
228 /* External signing. */
229 if (!pkey)
231 if (!session->internals.sign_func)
232 return GNUTLS_E_INSUFFICIENT_CREDENTIALS;
234 return (*session->internals.sign_func)
235 (session, session->internals.sign_func_userdata,
236 cert->cert_type, &cert->raw, hash_concat, signature);
240 if (!_gnutls_version_has_selectable_sighash (ver))
241 return _gnutls_privkey_sign_hash (pkey, hash_concat, signature);
242 else
243 return gnutls_privkey_sign_hash (pkey, hash_algo, 0, hash_concat, signature);
246 static int
247 verify_tls_hash (gnutls_protocol_t ver, gnutls_cert * cert,
248 const gnutls_datum_t * hash_concat,
249 gnutls_datum_t * signature, size_t sha1pos,
250 gnutls_pk_algorithm_t pk_algo)
252 int ret;
253 gnutls_datum_t vdata;
255 if (cert == NULL || cert->version == 0)
256 { /* this is the only way to check
257 * if it is initialized
259 gnutls_assert ();
260 return GNUTLS_E_CERTIFICATE_ERROR;
263 /* If the certificate supports signing continue.
265 if (cert->key_usage != 0)
266 if (!(cert->key_usage & GNUTLS_KEY_DIGITAL_SIGNATURE))
268 gnutls_assert ();
269 return GNUTLS_E_KEY_USAGE_VIOLATION;
272 if (pk_algo == GNUTLS_PK_UNKNOWN)
273 pk_algo = cert->subject_pk_algorithm;
274 switch (pk_algo)
276 case GNUTLS_PK_RSA:
278 vdata.data = hash_concat->data;
279 vdata.size = hash_concat->size;
281 /* verify signature */
282 if (!_gnutls_version_has_selectable_sighash (ver))
283 ret = _gnutls_rsa_verify (&vdata, signature, cert->params,
284 cert->params_size, 1);
285 else
286 ret = pubkey_verify_sig( NULL, &vdata, signature, pk_algo,
287 cert->params, cert->params_size);
289 if (ret < 0)
291 gnutls_assert ();
292 return ret;
295 break;
296 case GNUTLS_PK_DSA:
298 vdata.data = &hash_concat->data[sha1pos];
299 vdata.size = hash_concat->size - sha1pos;
301 ret = pubkey_verify_sig( NULL, &vdata, signature, pk_algo,
302 cert->params, cert->params_size);
303 /* verify signature */
304 if (ret < 0)
306 gnutls_assert ();
307 return ret;
310 break;
311 default:
312 gnutls_assert ();
313 return GNUTLS_E_INTERNAL_ERROR;
318 return 0;
322 /* Generates a signature of all the random data and the parameters.
323 * Used in DHE_* ciphersuites.
326 _gnutls_handshake_verify_data (gnutls_session_t session, gnutls_cert * cert,
327 const gnutls_datum_t * params,
328 gnutls_datum_t * signature,
329 gnutls_sign_algorithm_t algo)
331 gnutls_datum_t dconcat;
332 int ret;
333 digest_hd_st td_md5;
334 digest_hd_st td_sha;
335 opaque concat[MAX_SIG_SIZE];
336 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
337 gnutls_digest_algorithm_t hash_algo;
339 if (_gnutls_version_has_selectable_sighash (ver))
341 _gnutls_handshake_log ("HSK[%p]: verify handshake data: using %s\n",
342 session, gnutls_sign_algorithm_get_name (algo));
344 ret = cert_compatible_with_sig(cert, ver, algo);
345 if (ret < 0)
346 return gnutls_assert_val(ret);
348 ret = _gnutls_session_sign_algo_enabled (session, algo);
349 if (ret < 0)
350 return gnutls_assert_val(ret);
352 hash_algo = _gnutls_sign_get_hash_algorithm (algo);
354 else
356 ret = _gnutls_hash_init (&td_md5, GNUTLS_MAC_MD5);
357 if (ret < 0)
359 gnutls_assert ();
360 return ret;
363 _gnutls_hash (&td_md5, session->security_parameters.client_random,
364 GNUTLS_RANDOM_SIZE);
365 _gnutls_hash (&td_md5, session->security_parameters.server_random,
366 GNUTLS_RANDOM_SIZE);
367 _gnutls_hash (&td_md5, params->data, params->size);
369 hash_algo = GNUTLS_DIG_SHA1;
372 ret = _gnutls_hash_init (&td_sha, hash_algo);
373 if (ret < 0)
375 gnutls_assert ();
376 if (!_gnutls_version_has_selectable_sighash (ver))
377 _gnutls_hash_deinit (&td_md5, NULL);
378 return ret;
381 _gnutls_hash (&td_sha, session->security_parameters.client_random,
382 GNUTLS_RANDOM_SIZE);
383 _gnutls_hash (&td_sha, session->security_parameters.server_random,
384 GNUTLS_RANDOM_SIZE);
385 _gnutls_hash (&td_sha, params->data, params->size);
387 if (!_gnutls_version_has_selectable_sighash (ver))
389 _gnutls_hash_deinit (&td_md5, concat);
390 _gnutls_hash_deinit (&td_sha, &concat[16]);
391 dconcat.data = concat;
392 dconcat.size = 36;
394 else
396 _gnutls_hash_deinit (&td_sha, concat);
398 dconcat.data = concat;
399 dconcat.size = _gnutls_hash_get_algo_len (hash_algo);
402 ret = verify_tls_hash (ver, cert, &dconcat, signature,
403 dconcat.size -
404 _gnutls_hash_get_algo_len (hash_algo),
405 _gnutls_sign_get_pk_algorithm (algo));
406 if (ret < 0)
408 gnutls_assert ();
409 return ret;
412 return ret;
416 /* Client certificate verify calculations
419 /* this is _gnutls_handshake_verify_cert_vrfy for TLS 1.2
421 static int
422 _gnutls_handshake_verify_cert_vrfy12 (gnutls_session_t session,
423 gnutls_cert * cert,
424 gnutls_datum_t * signature,
425 gnutls_sign_algorithm_t sign_algo)
427 int ret;
428 opaque concat[MAX_SIG_SIZE];
429 digest_hd_st td;
430 gnutls_datum_t dconcat;
431 gnutls_sign_algorithm_t _sign_algo;
432 gnutls_digest_algorithm_t hash_algo;
433 digest_hd_st *handshake_td;
434 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
436 handshake_td = &session->internals.handshake_mac_handle.tls12.sha1;
437 hash_algo = handshake_td->algorithm;
438 _sign_algo =
439 _gnutls_x509_pk_to_sign (cert->subject_pk_algorithm, hash_algo);
441 if (_sign_algo != sign_algo)
443 handshake_td = &session->internals.handshake_mac_handle.tls12.sha256;
444 hash_algo = handshake_td->algorithm;
445 _sign_algo =
446 _gnutls_x509_pk_to_sign (cert->subject_pk_algorithm, hash_algo);
447 if (sign_algo != _sign_algo)
449 gnutls_assert ();
450 return GNUTLS_E_UNSUPPORTED_SIGNATURE_ALGORITHM;
454 ret = _gnutls_hash_copy (&td, handshake_td);
455 if (ret < 0)
457 gnutls_assert ();
458 return GNUTLS_E_HASH_FAILED;
461 _gnutls_hash_deinit (&td, concat);
463 dconcat.data = concat;
464 dconcat.size = _gnutls_hash_get_algo_len (hash_algo);
466 ret =
467 verify_tls_hash (ver, cert, &dconcat, signature, 0,
468 cert->subject_pk_algorithm);
469 if (ret < 0)
471 gnutls_assert ();
472 return ret;
475 return ret;
479 /* Verifies a TLS signature (like the one in the client certificate
480 * verify message).
483 _gnutls_handshake_verify_cert_vrfy (gnutls_session_t session,
484 gnutls_cert * cert,
485 gnutls_datum_t * signature,
486 gnutls_sign_algorithm_t sign_algo)
488 int ret;
489 opaque concat[MAX_SIG_SIZE];
490 digest_hd_st td_md5;
491 digest_hd_st td_sha;
492 gnutls_datum_t dconcat;
493 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
495 _gnutls_handshake_log ("HSK[%p]: verify cert vrfy: using %s\n",
496 session, gnutls_sign_algorithm_get_name (sign_algo));
498 if (session->security_parameters.handshake_mac_handle_type ==
499 HANDSHAKE_MAC_TYPE_12)
501 return _gnutls_handshake_verify_cert_vrfy12 (session, cert, signature,
502 sign_algo);
504 else if (session->security_parameters.handshake_mac_handle_type !=
505 HANDSHAKE_MAC_TYPE_10)
507 gnutls_assert ();
508 return GNUTLS_E_INTERNAL_ERROR;
511 ret =
512 _gnutls_hash_copy (&td_md5,
513 &session->internals.handshake_mac_handle.tls10.md5);
514 if (ret < 0)
516 gnutls_assert ();
517 return ret;
520 ret =
521 _gnutls_hash_copy (&td_sha,
522 &session->internals.handshake_mac_handle.tls10.sha);
523 if (ret < 0)
525 gnutls_assert ();
526 _gnutls_hash_deinit (&td_md5, NULL);
527 return GNUTLS_E_HASH_FAILED;
530 if (ver == GNUTLS_SSL3)
532 ret = _gnutls_generate_master (session, 1);
533 if (ret < 0)
535 gnutls_assert ();
536 return ret;
539 _gnutls_mac_deinit_ssl3_handshake (&td_md5, concat,
540 session->
541 security_parameters.master_secret,
542 GNUTLS_MASTER_SIZE);
543 _gnutls_mac_deinit_ssl3_handshake (&td_sha, &concat[16],
544 session->
545 security_parameters.master_secret,
546 GNUTLS_MASTER_SIZE);
548 else
550 _gnutls_hash_deinit (&td_md5, concat);
551 _gnutls_hash_deinit (&td_sha, &concat[16]);
554 dconcat.data = concat;
555 dconcat.size = 20 + 16; /* md5+ sha */
557 ret =
558 verify_tls_hash (ver, cert, &dconcat, signature, 16,
559 cert->subject_pk_algorithm);
560 if (ret < 0)
562 gnutls_assert ();
563 return ret;
566 return ret;
570 /* the same as _gnutls_handshake_sign_cert_vrfy except that it is made for TLS 1.2
572 static int
573 _gnutls_handshake_sign_cert_vrfy12 (gnutls_session_t session,
574 gnutls_cert * cert, gnutls_privkey_t pkey,
575 gnutls_datum_t * signature)
577 gnutls_datum_t dconcat;
578 int ret;
579 opaque concat[MAX_SIG_SIZE];
580 digest_hd_st td;
581 gnutls_sign_algorithm_t sign_algo;
582 gnutls_digest_algorithm_t hash_algo;
583 digest_hd_st *handshake_td;
585 sign_algo =
586 _gnutls_session_get_sign_algo (session, cert);
587 if (sign_algo == GNUTLS_SIGN_UNKNOWN)
589 gnutls_assert ();
590 return GNUTLS_E_UNKNOWN_PK_ALGORITHM;
593 hash_algo = _gnutls_sign_get_hash_algorithm (sign_algo);
595 _gnutls_debug_log ("sign handshake cert vrfy: picked %s with %s\n",
596 gnutls_sign_algorithm_get_name (sign_algo),
597 gnutls_mac_get_name (hash_algo));
599 if ((gnutls_mac_algorithm_t)hash_algo == session->internals.handshake_mac_handle.tls12.sha1.algorithm)
600 handshake_td = &session->internals.handshake_mac_handle.tls12.sha1;
601 else if ((gnutls_mac_algorithm_t)hash_algo == session->internals.handshake_mac_handle.tls12.sha256.algorithm)
602 handshake_td = &session->internals.handshake_mac_handle.tls12.sha256;
603 else
604 return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR); /* too bad we only support SHA1 and SHA256 */
606 ret = _gnutls_hash_copy (&td, handshake_td);
607 if (ret < 0)
609 gnutls_assert ();
610 return ret;
613 _gnutls_hash_deinit (&td, concat);
615 dconcat.data = concat;
616 dconcat.size = _gnutls_hash_get_algo_len (hash_algo);
618 ret = sign_tls_hash (session, hash_algo, cert, pkey, &dconcat, signature);
619 if (ret < 0)
621 gnutls_assert ();
622 return ret;
625 return sign_algo;
629 /* Generates a signature of all the previous sent packets in the
630 * handshake procedure.
631 * 20040227: now it works for SSL 3.0 as well
632 * 20091031: works for TLS 1.2 too!
634 * For TLS1.x, x<2 returns negative for failure and zero or unspecified for success.
635 * For TLS1.2 returns the signature algorithm used on success, or a negative value;
638 _gnutls_handshake_sign_cert_vrfy (gnutls_session_t session,
639 gnutls_cert * cert, gnutls_privkey_t pkey,
640 gnutls_datum_t * signature)
642 gnutls_datum_t dconcat;
643 int ret, hash_algo;
644 opaque concat[MAX_SIG_SIZE];
645 digest_hd_st td_md5;
646 digest_hd_st td_sha;
647 gnutls_protocol_t ver = gnutls_protocol_get_version (session);
649 if (session->security_parameters.handshake_mac_handle_type ==
650 HANDSHAKE_MAC_TYPE_12)
652 return _gnutls_handshake_sign_cert_vrfy12 (session, cert, pkey,
653 signature);
655 else if (session->security_parameters.handshake_mac_handle_type !=
656 HANDSHAKE_MAC_TYPE_10)
658 gnutls_assert ();
659 return GNUTLS_E_INTERNAL_ERROR;
662 ret =
663 _gnutls_hash_copy (&td_sha,
664 &session->internals.handshake_mac_handle.tls10.sha);
665 if (ret < 0)
667 gnutls_assert ();
668 return ret;
671 if (ver == GNUTLS_SSL3)
673 ret = _gnutls_generate_master (session, 1);
674 if (ret < 0)
676 gnutls_assert ();
677 return ret;
680 _gnutls_mac_deinit_ssl3_handshake (&td_sha, &concat[16],
681 session->
682 security_parameters.master_secret,
683 GNUTLS_MASTER_SIZE);
685 else
686 _gnutls_hash_deinit (&td_sha, &concat[16]);
688 switch (cert->subject_pk_algorithm)
690 case GNUTLS_PK_RSA:
691 ret =
692 _gnutls_hash_copy (&td_md5,
693 &session->internals.handshake_mac_handle.tls10.
694 md5);
695 if (ret < 0)
697 gnutls_assert ();
698 return ret;
701 if (ver == GNUTLS_SSL3)
702 _gnutls_mac_deinit_ssl3_handshake (&td_md5, concat,
703 session->
704 security_parameters.master_secret,
705 GNUTLS_MASTER_SIZE);
706 else
707 _gnutls_hash_deinit (&td_md5, concat);
709 dconcat.data = concat;
710 dconcat.size = 36;
711 break;
712 case GNUTLS_PK_DSA:
713 /* ensure 1024 bit DSA keys are used */
714 hash_algo = _gnutls_dsa_q_to_hash (cert->params[1], NULL);
715 if (!_gnutls_version_has_selectable_sighash (ver) && hash_algo != GNUTLS_DIG_SHA1)
716 return gnutls_assert_val(GNUTLS_E_INCOMPAT_DSA_KEY_WITH_TLS_PROTOCOL);
718 dconcat.data = &concat[16];
719 dconcat.size = 20;
720 break;
722 default:
723 return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
725 ret = sign_tls_hash (session, GNUTLS_DIG_NULL, cert, pkey, &dconcat, signature);
726 if (ret < 0)
728 gnutls_assert ();
731 return ret;
735 pk_hash_data (gnutls_pk_algorithm_t pk, gnutls_digest_algorithm_t hash,
736 bigint_t * params,
737 const gnutls_datum_t * data, gnutls_datum_t * digest)
739 int ret;
741 digest->size = _gnutls_hash_get_algo_len (hash);
742 digest->data = gnutls_malloc (digest->size);
743 if (digest->data == NULL)
745 gnutls_assert ();
746 return GNUTLS_E_MEMORY_ERROR;
749 ret = _gnutls_hash_fast (hash, data->data, data->size, digest->data);
750 if (ret < 0)
752 gnutls_assert ();
753 goto cleanup;
756 return 0;
758 cleanup:
759 gnutls_free (digest->data);
760 return ret;
763 /* Writes the digest information and the digest in a DER encoded
764 * structure. The digest info is allocated and stored into the info structure.
766 static int
767 encode_ber_digest_info (gnutls_digest_algorithm_t hash,
768 const gnutls_datum_t * digest,
769 gnutls_datum_t * output)
771 ASN1_TYPE dinfo = ASN1_TYPE_EMPTY;
772 int result;
773 const char *algo;
774 opaque *tmp_output;
775 int tmp_output_size;
777 algo = _gnutls_x509_mac_to_oid ((gnutls_mac_algorithm_t) hash);
778 if (algo == NULL)
780 gnutls_assert ();
781 _gnutls_x509_log ("Hash algorithm: %d\n", hash);
782 return GNUTLS_E_UNKNOWN_PK_ALGORITHM;
785 if ((result = asn1_create_element (_gnutls_get_gnutls_asn (),
786 "GNUTLS.DigestInfo",
787 &dinfo)) != ASN1_SUCCESS)
789 gnutls_assert ();
790 return _gnutls_asn2err (result);
793 result = asn1_write_value (dinfo, "digestAlgorithm.algorithm", algo, 1);
794 if (result != ASN1_SUCCESS)
796 gnutls_assert ();
797 asn1_delete_structure (&dinfo);
798 return _gnutls_asn2err (result);
801 /* Write an ASN.1 NULL in the parameters field. This matches RFC
802 3279 and RFC 4055, although is arguable incorrect from a historic
803 perspective (see those documents for more information).
804 Regardless of what is correct, this appears to be what most
805 implementations do. */
806 result = asn1_write_value (dinfo, "digestAlgorithm.parameters",
807 ASN1_NULL, ASN1_NULL_SIZE);
808 if (result != ASN1_SUCCESS)
810 gnutls_assert ();
811 asn1_delete_structure (&dinfo);
812 return _gnutls_asn2err (result);
815 result = asn1_write_value (dinfo, "digest", digest->data, digest->size);
816 if (result != ASN1_SUCCESS)
818 gnutls_assert ();
819 asn1_delete_structure (&dinfo);
820 return _gnutls_asn2err (result);
823 tmp_output_size = 0;
824 asn1_der_coding (dinfo, "", NULL, &tmp_output_size, NULL);
826 tmp_output = gnutls_malloc (tmp_output_size);
827 if (output->data == NULL)
829 gnutls_assert ();
830 asn1_delete_structure (&dinfo);
831 return GNUTLS_E_MEMORY_ERROR;
834 result = asn1_der_coding (dinfo, "", tmp_output, &tmp_output_size, NULL);
835 if (result != ASN1_SUCCESS)
837 gnutls_assert ();
838 asn1_delete_structure (&dinfo);
839 return _gnutls_asn2err (result);
842 asn1_delete_structure (&dinfo);
844 output->size = tmp_output_size;
845 output->data = tmp_output;
847 return 0;
851 * This function will do RSA PKCS #1 1.5 encoding
852 * on the given digest. The given digest must be allocated
853 * and will be freed if replacement is required.
856 pk_prepare_hash (gnutls_pk_algorithm_t pk,
857 gnutls_digest_algorithm_t hash, gnutls_datum_t * digest)
859 int ret;
860 gnutls_datum old_digest = { digest->data, digest->size };
862 switch (pk)
864 case GNUTLS_PK_RSA:
865 /* Encode the digest as a DigestInfo
867 if ((ret = encode_ber_digest_info (hash, &old_digest, digest)) != 0)
869 gnutls_assert ();
870 return ret;
873 _gnutls_free_datum (&old_digest);
874 break;
875 case GNUTLS_PK_DSA:
876 break;
877 default:
878 gnutls_assert ();
879 return GNUTLS_E_UNIMPLEMENTED_FEATURE;
882 return 0;