2 * Copyright (c) 2004 - 2007 Kungliga Tekniska Högskolan
3 * (Royal Institute of Technology, Stockholm, Sweden).
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * 3. Neither the name of the Institute nor the names of its contributors
18 * may be used to endorse or promote products derived from this software
19 * without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
45 struct hx509_generate_private_context
{
46 const heim_oid
*key_oid
;
48 unsigned long num_bits
;
51 struct hx509_private_key_ops
{
53 const heim_oid
*(*key_oid
)(void);
54 int (*get_spki
)(hx509_context
,
55 const hx509_private_key
,
56 SubjectPublicKeyInfo
*);
57 int (*export
)(hx509_context context
,
58 const hx509_private_key
,
60 int (*import
)(hx509_context
,
63 hx509_private_key private_key
);
64 int (*generate_private_key
)(hx509_context
,
65 struct hx509_generate_private_context
*,
67 BIGNUM
*(*get_internal
)(hx509_context
, hx509_private_key
, const char *);
68 int (*handle_alg
)(const hx509_private_key
,
69 const AlgorithmIdentifier
*,
71 int (*sign
)(hx509_context context
,
72 const hx509_private_key
,
73 const AlgorithmIdentifier
*,
74 const heim_octet_string
*,
75 AlgorithmIdentifier
*,
78 const AlgorithmIdentifier
*(*preferred_sig_alg
)
79 (const hx509_private_key
,
80 const hx509_peer_info
);
81 int (*unwrap
)(hx509_context context
,
82 const hx509_private_key
,
83 const AlgorithmIdentifier
*,
84 const heim_octet_string
*,
89 struct hx509_private_key
{
91 const struct signature_alg
*md
;
92 const heim_oid
*signature_alg
;
97 /* new crypto layer */
98 hx509_private_key_ops
*ops
;
105 struct signature_alg
{
107 const heim_oid
*(*sig_oid
)(void);
108 const AlgorithmIdentifier
*(*sig_alg
)(void);
109 const heim_oid
*(*key_oid
)(void);
110 const heim_oid
*(*digest_oid
)(void);
112 #define PROVIDE_CONF 1
113 #define REQUIRE_SIGNER 2
115 #define SIG_DIGEST 0x100
116 #define SIG_PUBLIC_SIG 0x200
117 #define SIG_SECRET 0x400
119 #define RA_RSA_USES_DIGEST_INFO 0x1000000
122 int (*verify_signature
)(hx509_context context
,
123 const struct signature_alg
*,
125 const AlgorithmIdentifier
*,
126 const heim_octet_string
*,
127 const heim_octet_string
*);
128 int (*create_signature
)(hx509_context
,
129 const struct signature_alg
*,
130 const hx509_private_key
,
131 const AlgorithmIdentifier
*,
132 const heim_octet_string
*,
133 AlgorithmIdentifier
*,
134 heim_octet_string
*);
142 heim_int2BN(const heim_integer
*i
)
146 bn
= BN_bin2bn(i
->data
, i
->length
, NULL
);
147 BN_set_negative(bn
, i
->negative
);
156 set_digest_alg(DigestAlgorithmIdentifier
*id
,
158 const void *param
, size_t length
)
162 id
->parameters
= malloc(sizeof(*id
->parameters
));
163 if (id
->parameters
== NULL
)
165 id
->parameters
->data
= malloc(length
);
166 if (id
->parameters
->data
== NULL
) {
167 free(id
->parameters
);
168 id
->parameters
= NULL
;
171 memcpy(id
->parameters
->data
, param
, length
);
172 id
->parameters
->length
= length
;
174 id
->parameters
= NULL
;
175 ret
= der_copy_oid(oid
, &id
->algorithm
);
177 if (id
->parameters
) {
178 free(id
->parameters
->data
);
179 free(id
->parameters
);
180 id
->parameters
= NULL
;
192 rsa_verify_signature(hx509_context context
,
193 const struct signature_alg
*sig_alg
,
194 const Certificate
*signer
,
195 const AlgorithmIdentifier
*alg
,
196 const heim_octet_string
*data
,
197 const heim_octet_string
*sig
)
199 const SubjectPublicKeyInfo
*spi
;
208 memset(&di
, 0, sizeof(di
));
210 spi
= &signer
->tbsCertificate
.subjectPublicKeyInfo
;
214 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
217 ret
= decode_RSAPublicKey(spi
->subjectPublicKey
.data
,
218 spi
->subjectPublicKey
.length
/ 8,
221 hx509_set_error_string(context
, 0, ret
, "Failed to decode RSAPublicKey");
225 rsa
->n
= heim_int2BN(&pk
.modulus
);
226 rsa
->e
= heim_int2BN(&pk
.publicExponent
);
228 free_RSAPublicKey(&pk
);
230 if (rsa
->n
== NULL
|| rsa
->e
== NULL
) {
232 hx509_set_error_string(context
, 0, ret
, "out of memory");
236 tosize
= RSA_size(rsa
);
240 hx509_set_error_string(context
, 0, ret
, "out of memory");
244 retsize
= RSA_public_decrypt(sig
->length
, (unsigned char *)sig
->data
,
245 to
, rsa
, RSA_PKCS1_PADDING
);
247 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
248 hx509_set_error_string(context
, 0, ret
,
249 "RSA public decrypt failed: %d", retsize
);
253 if (retsize
> tosize
)
254 _hx509_abort("internal rsa decryption failure: ret > tosize");
256 if (sig_alg
->flags
& RA_RSA_USES_DIGEST_INFO
) {
258 ret
= decode_DigestInfo(to
, retsize
, &di
, &size
);
264 /* Check for extra data inside the sigature */
265 if (size
!= retsize
) {
266 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
267 hx509_set_error_string(context
, 0, ret
, "size from decryption mismatch");
271 if (sig_alg
->digest_oid
&&
272 der_heim_oid_cmp(&di
.digestAlgorithm
.algorithm
,
273 (*sig_alg
->digest_oid
)()) != 0)
275 ret
= HX509_CRYPTO_OID_MISMATCH
;
276 hx509_set_error_string(context
, 0, ret
, "object identifier in RSA sig mismatch");
280 /* verify that the parameters are NULL or the NULL-type */
281 if (di
.digestAlgorithm
.parameters
!= NULL
&&
282 (di
.digestAlgorithm
.parameters
->length
!= 2 ||
283 memcmp(di
.digestAlgorithm
.parameters
->data
, "\x05\x00", 2) != 0))
285 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
286 hx509_set_error_string(context
, 0, ret
, "Extra parameters inside RSA signature");
290 ret
= _hx509_verify_signature(context
,
296 if (retsize
!= data
->length
||
297 memcmp(to
, data
->data
, retsize
) != 0)
299 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
300 hx509_set_error_string(context
, 0, ret
, "RSA Signature incorrect");
307 free_DigestInfo(&di
);
313 rsa_create_signature(hx509_context context
,
314 const struct signature_alg
*sig_alg
,
315 const hx509_private_key signer
,
316 const AlgorithmIdentifier
*alg
,
317 const heim_octet_string
*data
,
318 AlgorithmIdentifier
*signatureAlgorithm
,
319 heim_octet_string
*sig
)
321 const AlgorithmIdentifier
*digest_alg
;
322 heim_octet_string indata
;
323 const heim_oid
*sig_oid
;
328 sig_oid
= &alg
->algorithm
;
330 sig_oid
= signer
->signature_alg
;
332 if (der_heim_oid_cmp(sig_oid
, oid_id_pkcs1_sha256WithRSAEncryption()) == 0) {
333 digest_alg
= hx509_signature_sha256();
334 } else if (der_heim_oid_cmp(sig_oid
, oid_id_pkcs1_sha1WithRSAEncryption()) == 0) {
335 digest_alg
= hx509_signature_sha1();
336 } else if (der_heim_oid_cmp(sig_oid
, oid_id_pkcs1_md5WithRSAEncryption()) == 0) {
337 digest_alg
= hx509_signature_md5();
338 } else if (der_heim_oid_cmp(sig_oid
, oid_id_pkcs1_md5WithRSAEncryption()) == 0) {
339 digest_alg
= hx509_signature_md5();
340 } else if (der_heim_oid_cmp(sig_oid
, oid_id_dsa_with_sha1()) == 0) {
341 digest_alg
= hx509_signature_sha1();
342 } else if (der_heim_oid_cmp(sig_oid
, oid_id_pkcs1_rsaEncryption()) == 0) {
343 digest_alg
= hx509_signature_sha1();
344 } else if (der_heim_oid_cmp(sig_oid
, oid_id_heim_rsa_pkcs1_x509()) == 0) {
347 return HX509_ALG_NOT_SUPP
;
349 if (signatureAlgorithm
) {
350 ret
= set_digest_alg(signatureAlgorithm
, sig_oid
, "\x05\x00", 2);
352 hx509_clear_error_string(context
);
359 memset(&di
, 0, sizeof(di
));
361 ret
= _hx509_create_signature(context
,
369 ASN1_MALLOC_ENCODE(DigestInfo
,
375 free_DigestInfo(&di
);
377 hx509_set_error_string(context
, 0, ret
, "out of memory");
380 if (indata
.length
!= size
)
381 _hx509_abort("internal ASN.1 encoder error");
386 sig
->length
= RSA_size(signer
->private_key
.rsa
);
387 sig
->data
= malloc(sig
->length
);
388 if (sig
->data
== NULL
) {
389 der_free_octet_string(&indata
);
390 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
394 ret
= RSA_private_encrypt(indata
.length
, indata
.data
,
396 signer
->private_key
.rsa
,
398 if (indata
.data
!= data
->data
)
399 der_free_octet_string(&indata
);
401 ret
= HX509_CMS_FAILED_CREATE_SIGATURE
;
402 hx509_set_error_string(context
, 0, ret
,
403 "RSA private decrypt failed: %d", ret
);
406 if (ret
> sig
->length
)
407 _hx509_abort("RSA signature prelen longer the output len");
415 rsa_private_key_import(hx509_context context
,
418 hx509_private_key private_key
)
420 const unsigned char *p
= data
;
422 private_key
->private_key
.rsa
=
423 d2i_RSAPrivateKey(NULL
, &p
, len
);
424 if (private_key
->private_key
.rsa
== NULL
) {
425 hx509_set_error_string(context
, 0, HX509_PARSING_KEY_FAILED
,
426 "Failed to parse RSA key");
427 return HX509_PARSING_KEY_FAILED
;
429 private_key
->signature_alg
= oid_id_pkcs1_sha1WithRSAEncryption();
435 rsa_private_key2SPKI(hx509_context context
,
436 hx509_private_key private_key
,
437 SubjectPublicKeyInfo
*spki
)
441 memset(spki
, 0, sizeof(*spki
));
443 len
= i2d_RSAPublicKey(private_key
->private_key
.rsa
, NULL
);
445 spki
->subjectPublicKey
.data
= malloc(len
);
446 if (spki
->subjectPublicKey
.data
== NULL
) {
447 hx509_set_error_string(context
, 0, ENOMEM
, "malloc - out of memory");
450 spki
->subjectPublicKey
.length
= len
* 8;
452 ret
= set_digest_alg(&spki
->algorithm
,oid_id_pkcs1_rsaEncryption(),
455 hx509_set_error_string(context
, 0, ret
, "malloc - out of memory");
456 free(spki
->subjectPublicKey
.data
);
457 spki
->subjectPublicKey
.data
= NULL
;
458 spki
->subjectPublicKey
.length
= 0;
463 unsigned char *pp
= spki
->subjectPublicKey
.data
;
464 i2d_RSAPublicKey(private_key
->private_key
.rsa
, &pp
);
471 rsa_generate_private_key(hx509_context context
,
472 struct hx509_generate_private_context
*ctx
,
473 hx509_private_key private_key
)
479 static const int default_rsa_e
= 65537;
480 static const int default_rsa_bits
= 1024;
482 private_key
->private_key
.rsa
= RSA_new();
483 if (private_key
->private_key
.rsa
== NULL
) {
484 hx509_set_error_string(context
, 0, HX509_PARSING_KEY_FAILED
,
485 "Failed to generate RSA key");
486 return HX509_PARSING_KEY_FAILED
;
490 BN_set_word(e
, default_rsa_e
);
492 bits
= default_rsa_bits
;
495 bits
= ctx
->num_bits
;
499 ret
= RSA_generate_key_ex(private_key
->private_key
.rsa
, bits
, e
, NULL
);
502 hx509_set_error_string(context
, 0, HX509_PARSING_KEY_FAILED
,
503 "Failed to generate RSA key");
504 return HX509_PARSING_KEY_FAILED
;
506 private_key
->signature_alg
= oid_id_pkcs1_sha1WithRSAEncryption();
512 rsa_private_key_export(hx509_context context
,
513 const hx509_private_key key
,
514 heim_octet_string
*data
)
521 ret
= i2d_RSAPrivateKey(key
->private_key
.rsa
, NULL
);
524 hx509_set_error_string(context
, 0, ret
,
525 "Private key is not exportable");
529 data
->data
= malloc(ret
);
530 if (data
->data
== NULL
) {
532 hx509_set_error_string(context
, 0, ret
, "malloc out of memory");
538 unsigned char *p
= data
->data
;
539 i2d_RSAPrivateKey(key
->private_key
.rsa
, &p
);
546 rsa_get_internal(hx509_context context
, hx509_private_key key
, const char *type
)
548 if (strcasecmp(type
, "rsa-modulus") == 0) {
549 return BN_dup(key
->private_key
.rsa
->n
);
550 } else if (strcasecmp(type
, "rsa-exponent") == 0) {
551 return BN_dup(key
->private_key
.rsa
->e
);
558 static hx509_private_key_ops rsa_private_key_ops
= {
560 oid_id_pkcs1_rsaEncryption
,
561 rsa_private_key2SPKI
,
562 rsa_private_key_export
,
563 rsa_private_key_import
,
564 rsa_generate_private_key
,
574 dsa_verify_signature(hx509_context context
,
575 const struct signature_alg
*sig_alg
,
576 const Certificate
*signer
,
577 const AlgorithmIdentifier
*alg
,
578 const heim_octet_string
*data
,
579 const heim_octet_string
*sig
)
581 const SubjectPublicKeyInfo
*spi
;
588 spi
= &signer
->tbsCertificate
.subjectPublicKeyInfo
;
592 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
596 ret
= decode_DSAPublicKey(spi
->subjectPublicKey
.data
,
597 spi
->subjectPublicKey
.length
/ 8,
602 dsa
->pub_key
= heim_int2BN(&pk
);
604 free_DSAPublicKey(&pk
);
606 if (dsa
->pub_key
== NULL
) {
608 hx509_set_error_string(context
, 0, ret
, "out of memory");
612 if (spi
->algorithm
.parameters
== NULL
) {
613 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
614 hx509_set_error_string(context
, 0, ret
, "DSA parameters missing");
618 ret
= decode_DSAParams(spi
->algorithm
.parameters
->data
,
619 spi
->algorithm
.parameters
->length
,
623 hx509_set_error_string(context
, 0, ret
, "DSA parameters failed to decode");
627 dsa
->p
= heim_int2BN(¶m
.p
);
628 dsa
->q
= heim_int2BN(¶m
.q
);
629 dsa
->g
= heim_int2BN(¶m
.g
);
631 free_DSAParams(¶m
);
633 if (dsa
->p
== NULL
|| dsa
->q
== NULL
|| dsa
->g
== NULL
) {
635 hx509_set_error_string(context
, 0, ret
, "out of memory");
639 ret
= DSA_verify(-1, data
->data
, data
->length
,
640 (unsigned char*)sig
->data
, sig
->length
,
644 else if (ret
== 0 || ret
== -1) {
645 ret
= HX509_CRYPTO_BAD_SIGNATURE
;
646 hx509_set_error_string(context
, 0, ret
, "BAD DSA sigature");
648 ret
= HX509_CRYPTO_SIG_INVALID_FORMAT
;
649 hx509_set_error_string(context
, 0, ret
, "Invalid format of DSA sigature");
660 dsa_parse_private_key(hx509_context context
,
663 hx509_private_key private_key
)
665 const unsigned char *p
= data
;
667 private_key
->private_key
.dsa
=
668 d2i_DSAPrivateKey(NULL
, &p
, len
);
669 if (private_key
->private_key
.dsa
== NULL
)
671 private_key
->signature_alg
= oid_id_dsa_with_sha1();
675 hx509_set_error_string(context
, 0, HX509_PARSING_KEY_FAILED
,
676 "No support to parse DSA keys");
677 return HX509_PARSING_KEY_FAILED
;
683 sha1_verify_signature(hx509_context context
,
684 const struct signature_alg
*sig_alg
,
685 const Certificate
*signer
,
686 const AlgorithmIdentifier
*alg
,
687 const heim_octet_string
*data
,
688 const heim_octet_string
*sig
)
690 unsigned char digest
[SHA_DIGEST_LENGTH
];
693 if (sig
->length
!= SHA_DIGEST_LENGTH
) {
694 hx509_set_error_string(context
, 0, HX509_CRYPTO_SIG_INVALID_FORMAT
,
695 "SHA1 sigature have wrong length");
696 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
700 SHA1_Update(&m
, data
->data
, data
->length
);
701 SHA1_Final (digest
, &m
);
703 if (memcmp(digest
, sig
->data
, SHA_DIGEST_LENGTH
) != 0) {
704 hx509_set_error_string(context
, 0, HX509_CRYPTO_BAD_SIGNATURE
,
705 "Bad SHA1 sigature");
706 return HX509_CRYPTO_BAD_SIGNATURE
;
713 sha256_create_signature(hx509_context context
,
714 const struct signature_alg
*sig_alg
,
715 const hx509_private_key signer
,
716 const AlgorithmIdentifier
*alg
,
717 const heim_octet_string
*data
,
718 AlgorithmIdentifier
*signatureAlgorithm
,
719 heim_octet_string
*sig
)
723 memset(sig
, 0, sizeof(*sig
));
725 if (signatureAlgorithm
) {
727 ret
= set_digest_alg(signatureAlgorithm
, (*sig_alg
->sig_oid
)(),
734 sig
->data
= malloc(SHA256_DIGEST_LENGTH
);
735 if (sig
->data
== NULL
) {
739 sig
->length
= SHA256_DIGEST_LENGTH
;
742 SHA256_Update(&m
, data
->data
, data
->length
);
743 SHA256_Final (sig
->data
, &m
);
749 sha256_verify_signature(hx509_context context
,
750 const struct signature_alg
*sig_alg
,
751 const Certificate
*signer
,
752 const AlgorithmIdentifier
*alg
,
753 const heim_octet_string
*data
,
754 const heim_octet_string
*sig
)
756 unsigned char digest
[SHA256_DIGEST_LENGTH
];
759 if (sig
->length
!= SHA256_DIGEST_LENGTH
) {
760 hx509_set_error_string(context
, 0, HX509_CRYPTO_SIG_INVALID_FORMAT
,
761 "SHA256 sigature have wrong length");
762 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
766 SHA256_Update(&m
, data
->data
, data
->length
);
767 SHA256_Final (digest
, &m
);
769 if (memcmp(digest
, sig
->data
, SHA256_DIGEST_LENGTH
) != 0) {
770 hx509_set_error_string(context
, 0, HX509_CRYPTO_BAD_SIGNATURE
,
771 "Bad SHA256 sigature");
772 return HX509_CRYPTO_BAD_SIGNATURE
;
779 sha1_create_signature(hx509_context context
,
780 const struct signature_alg
*sig_alg
,
781 const hx509_private_key signer
,
782 const AlgorithmIdentifier
*alg
,
783 const heim_octet_string
*data
,
784 AlgorithmIdentifier
*signatureAlgorithm
,
785 heim_octet_string
*sig
)
789 memset(sig
, 0, sizeof(*sig
));
791 if (signatureAlgorithm
) {
793 ret
= set_digest_alg(signatureAlgorithm
, (*sig_alg
->sig_oid
)(),
800 sig
->data
= malloc(SHA_DIGEST_LENGTH
);
801 if (sig
->data
== NULL
) {
805 sig
->length
= SHA_DIGEST_LENGTH
;
808 SHA1_Update(&m
, data
->data
, data
->length
);
809 SHA1_Final (sig
->data
, &m
);
815 md5_verify_signature(hx509_context context
,
816 const struct signature_alg
*sig_alg
,
817 const Certificate
*signer
,
818 const AlgorithmIdentifier
*alg
,
819 const heim_octet_string
*data
,
820 const heim_octet_string
*sig
)
822 unsigned char digest
[MD5_DIGEST_LENGTH
];
825 if (sig
->length
!= MD5_DIGEST_LENGTH
) {
826 hx509_set_error_string(context
, 0, HX509_CRYPTO_SIG_INVALID_FORMAT
,
827 "MD5 sigature have wrong length");
828 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
832 MD5_Update(&m
, data
->data
, data
->length
);
833 MD5_Final (digest
, &m
);
835 if (memcmp(digest
, sig
->data
, MD5_DIGEST_LENGTH
) != 0) {
836 hx509_set_error_string(context
, 0, HX509_CRYPTO_BAD_SIGNATURE
,
838 return HX509_CRYPTO_BAD_SIGNATURE
;
845 md2_verify_signature(hx509_context context
,
846 const struct signature_alg
*sig_alg
,
847 const Certificate
*signer
,
848 const AlgorithmIdentifier
*alg
,
849 const heim_octet_string
*data
,
850 const heim_octet_string
*sig
)
852 unsigned char digest
[MD2_DIGEST_LENGTH
];
855 if (sig
->length
!= MD2_DIGEST_LENGTH
) {
856 hx509_set_error_string(context
, 0, HX509_CRYPTO_SIG_INVALID_FORMAT
,
857 "MD2 sigature have wrong length");
858 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
862 MD2_Update(&m
, data
->data
, data
->length
);
863 MD2_Final (digest
, &m
);
865 if (memcmp(digest
, sig
->data
, MD2_DIGEST_LENGTH
) != 0) {
866 hx509_set_error_string(context
, 0, HX509_CRYPTO_BAD_SIGNATURE
,
868 return HX509_CRYPTO_BAD_SIGNATURE
;
874 static const struct signature_alg heim_rsa_pkcs1_x509
= {
876 oid_id_heim_rsa_pkcs1_x509
,
877 hx509_signature_rsa_pkcs1_x509
,
878 oid_id_pkcs1_rsaEncryption
,
880 PROVIDE_CONF
|REQUIRE_SIGNER
|SIG_PUBLIC_SIG
,
881 rsa_verify_signature
,
885 static const struct signature_alg pkcs1_rsa_sha1_alg
= {
887 oid_id_pkcs1_rsaEncryption
,
888 hx509_signature_rsa_with_sha1
,
889 oid_id_pkcs1_rsaEncryption
,
891 PROVIDE_CONF
|REQUIRE_SIGNER
|RA_RSA_USES_DIGEST_INFO
|SIG_PUBLIC_SIG
,
892 rsa_verify_signature
,
896 static const struct signature_alg rsa_with_sha256_alg
= {
898 oid_id_pkcs1_sha256WithRSAEncryption
,
899 hx509_signature_rsa_with_sha256
,
900 oid_id_pkcs1_rsaEncryption
,
902 PROVIDE_CONF
|REQUIRE_SIGNER
|RA_RSA_USES_DIGEST_INFO
|SIG_PUBLIC_SIG
,
903 rsa_verify_signature
,
907 static const struct signature_alg rsa_with_sha1_alg
= {
909 oid_id_pkcs1_sha1WithRSAEncryption
,
910 hx509_signature_rsa_with_sha1
,
911 oid_id_pkcs1_rsaEncryption
,
913 PROVIDE_CONF
|REQUIRE_SIGNER
|RA_RSA_USES_DIGEST_INFO
|SIG_PUBLIC_SIG
,
914 rsa_verify_signature
,
918 static const struct signature_alg rsa_with_md5_alg
= {
920 oid_id_pkcs1_md5WithRSAEncryption
,
921 hx509_signature_rsa_with_md5
,
922 oid_id_pkcs1_rsaEncryption
,
923 oid_id_rsa_digest_md5
,
924 PROVIDE_CONF
|REQUIRE_SIGNER
|RA_RSA_USES_DIGEST_INFO
|SIG_PUBLIC_SIG
,
925 rsa_verify_signature
,
929 static const struct signature_alg rsa_with_md2_alg
= {
931 oid_id_pkcs1_md2WithRSAEncryption
,
932 hx509_signature_rsa_with_md2
,
933 oid_id_pkcs1_rsaEncryption
,
934 oid_id_rsa_digest_md2
,
935 PROVIDE_CONF
|REQUIRE_SIGNER
|RA_RSA_USES_DIGEST_INFO
|SIG_PUBLIC_SIG
,
936 rsa_verify_signature
,
940 static const struct signature_alg dsa_sha1_alg
= {
942 oid_id_dsa_with_sha1
,
946 PROVIDE_CONF
|REQUIRE_SIGNER
|SIG_PUBLIC_SIG
,
947 dsa_verify_signature
,
948 /* create_signature */ NULL
,
951 static const struct signature_alg sha256_alg
= {
954 hx509_signature_sha256
,
958 sha256_verify_signature
,
959 sha256_create_signature
962 static const struct signature_alg sha1_alg
= {
965 hx509_signature_sha1
,
969 sha1_verify_signature
,
970 sha1_create_signature
973 static const struct signature_alg md5_alg
= {
975 oid_id_rsa_digest_md5
,
983 static const struct signature_alg md2_alg
= {
985 oid_id_rsa_digest_md2
,
994 * Order matter in this structure, "best" first for each "key
995 * compatible" type (type is RSA, DSA, none, etc)
998 static const struct signature_alg
*sig_algs
[] = {
999 &rsa_with_sha256_alg
,
1001 &pkcs1_rsa_sha1_alg
,
1004 &heim_rsa_pkcs1_x509
,
1013 static const struct signature_alg
*
1014 find_sig_alg(const heim_oid
*oid
)
1017 for (i
= 0; sig_algs
[i
]; i
++)
1018 if (der_heim_oid_cmp((*sig_algs
[i
]->sig_oid
)(), oid
) == 0)
1027 static struct hx509_private_key_ops
*private_algs
[] = {
1028 &rsa_private_key_ops
,
1032 static hx509_private_key_ops
*
1033 find_private_alg(const heim_oid
*oid
)
1036 for (i
= 0; private_algs
[i
]; i
++) {
1037 if (private_algs
[i
]->key_oid
== NULL
)
1039 if (der_heim_oid_cmp((*private_algs
[i
]->key_oid
)(), oid
) == 0)
1040 return private_algs
[i
];
1047 _hx509_verify_signature(hx509_context context
,
1048 const Certificate
*signer
,
1049 const AlgorithmIdentifier
*alg
,
1050 const heim_octet_string
*data
,
1051 const heim_octet_string
*sig
)
1053 const struct signature_alg
*md
;
1055 md
= find_sig_alg(&alg
->algorithm
);
1057 hx509_clear_error_string(context
);
1058 return HX509_SIG_ALG_NO_SUPPORTED
;
1060 if (signer
&& (md
->flags
& PROVIDE_CONF
) == 0) {
1061 hx509_clear_error_string(context
);
1062 return HX509_CRYPTO_SIG_NO_CONF
;
1064 if (signer
== NULL
&& (md
->flags
& REQUIRE_SIGNER
)) {
1065 hx509_clear_error_string(context
);
1066 return HX509_CRYPTO_SIGNATURE_WITHOUT_SIGNER
;
1068 if (md
->key_oid
&& signer
) {
1069 const SubjectPublicKeyInfo
*spi
;
1070 spi
= &signer
->tbsCertificate
.subjectPublicKeyInfo
;
1072 if (der_heim_oid_cmp(&spi
->algorithm
.algorithm
, (*md
->key_oid
)()) != 0) {
1073 hx509_clear_error_string(context
);
1074 return HX509_SIG_ALG_DONT_MATCH_KEY_ALG
;
1077 return (*md
->verify_signature
)(context
, md
, signer
, alg
, data
, sig
);
1081 _hx509_verify_signature_bitstring(hx509_context context
,
1082 const Certificate
*signer
,
1083 const AlgorithmIdentifier
*alg
,
1084 const heim_octet_string
*data
,
1085 const heim_bit_string
*sig
)
1087 heim_octet_string os
;
1089 if (sig
->length
& 7) {
1090 hx509_set_error_string(context
, 0, HX509_CRYPTO_SIG_INVALID_FORMAT
,
1091 "signature not multiple of 8 bits");
1092 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
1095 os
.data
= sig
->data
;
1096 os
.length
= sig
->length
/ 8;
1098 return _hx509_verify_signature(context
, signer
, alg
, data
, &os
);
1102 _hx509_create_signature(hx509_context context
,
1103 const hx509_private_key signer
,
1104 const AlgorithmIdentifier
*alg
,
1105 const heim_octet_string
*data
,
1106 AlgorithmIdentifier
*signatureAlgorithm
,
1107 heim_octet_string
*sig
)
1109 const struct signature_alg
*md
;
1111 if (signer
&& signer
->ops
&& signer
->ops
->handle_alg
&&
1112 (*signer
->ops
->handle_alg
)(signer
, alg
, COT_SIGN
))
1114 return (*signer
->ops
->sign
)(context
, signer
, alg
, data
,
1115 signatureAlgorithm
, sig
);
1118 md
= find_sig_alg(&alg
->algorithm
);
1120 hx509_set_error_string(context
, 0, HX509_SIG_ALG_NO_SUPPORTED
,
1121 "algorithm no supported");
1122 return HX509_SIG_ALG_NO_SUPPORTED
;
1125 if (signer
&& (md
->flags
& PROVIDE_CONF
) == 0) {
1126 hx509_set_error_string(context
, 0, HX509_SIG_ALG_NO_SUPPORTED
,
1127 "algorithm provides no conf");
1128 return HX509_CRYPTO_SIG_NO_CONF
;
1131 return (*md
->create_signature
)(context
, md
, signer
, alg
, data
,
1132 signatureAlgorithm
, sig
);
1136 _hx509_create_signature_bitstring(hx509_context context
,
1137 const hx509_private_key signer
,
1138 const AlgorithmIdentifier
*alg
,
1139 const heim_octet_string
*data
,
1140 AlgorithmIdentifier
*signatureAlgorithm
,
1141 heim_bit_string
*sig
)
1143 heim_octet_string os
;
1146 ret
= _hx509_create_signature(context
, signer
, alg
,
1147 data
, signatureAlgorithm
, &os
);
1150 sig
->data
= os
.data
;
1151 sig
->length
= os
.length
* 8;
1156 _hx509_public_encrypt(hx509_context context
,
1157 const heim_octet_string
*cleartext
,
1158 const Certificate
*cert
,
1159 heim_oid
*encryption_oid
,
1160 heim_octet_string
*ciphertext
)
1162 const SubjectPublicKeyInfo
*spi
;
1170 ciphertext
->data
= NULL
;
1171 ciphertext
->length
= 0;
1173 spi
= &cert
->tbsCertificate
.subjectPublicKeyInfo
;
1177 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1181 ret
= decode_RSAPublicKey(spi
->subjectPublicKey
.data
,
1182 spi
->subjectPublicKey
.length
/ 8,
1186 hx509_set_error_string(context
, 0, ret
, "RSAPublicKey decode failure");
1189 rsa
->n
= heim_int2BN(&pk
.modulus
);
1190 rsa
->e
= heim_int2BN(&pk
.publicExponent
);
1192 free_RSAPublicKey(&pk
);
1194 if (rsa
->n
== NULL
|| rsa
->e
== NULL
) {
1196 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1200 tosize
= RSA_size(rsa
);
1201 to
= malloc(tosize
);
1204 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1208 ret
= RSA_public_encrypt(cleartext
->length
,
1209 (unsigned char *)cleartext
->data
,
1210 to
, rsa
, RSA_PKCS1_PADDING
);
1214 hx509_set_error_string(context
, 0, HX509_CRYPTO_RSA_PUBLIC_ENCRYPT
,
1215 "RSA public encrypt failed with %d", ret
);
1216 return HX509_CRYPTO_RSA_PUBLIC_ENCRYPT
;
1219 _hx509_abort("internal rsa decryption failure: ret > tosize");
1221 ciphertext
->length
= ret
;
1222 ciphertext
->data
= to
;
1224 ret
= der_copy_oid(oid_id_pkcs1_rsaEncryption(), encryption_oid
);
1226 der_free_octet_string(ciphertext
);
1227 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1235 _hx509_private_key_private_decrypt(hx509_context context
,
1236 const heim_octet_string
*ciphertext
,
1237 const heim_oid
*encryption_oid
,
1238 hx509_private_key p
,
1239 heim_octet_string
*cleartext
)
1243 cleartext
->data
= NULL
;
1244 cleartext
->length
= 0;
1246 if (p
->private_key
.rsa
== NULL
) {
1247 hx509_set_error_string(context
, 0, HX509_PRIVATE_KEY_MISSING
,
1248 "Private RSA key missing");
1249 return HX509_PRIVATE_KEY_MISSING
;
1252 cleartext
->length
= RSA_size(p
->private_key
.rsa
);
1253 cleartext
->data
= malloc(cleartext
->length
);
1254 if (cleartext
->data
== NULL
) {
1255 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1258 ret
= RSA_private_decrypt(ciphertext
->length
, ciphertext
->data
,
1263 der_free_octet_string(cleartext
);
1264 hx509_set_error_string(context
, 0, HX509_CRYPTO_RSA_PRIVATE_DECRYPT
,
1265 "Failed to decrypt using private key: %d", ret
);
1266 return HX509_CRYPTO_RSA_PRIVATE_DECRYPT
;
1268 if (cleartext
->length
< ret
)
1269 _hx509_abort("internal rsa decryption failure: ret > tosize");
1271 cleartext
->length
= ret
;
1278 _hx509_parse_private_key(hx509_context context
,
1279 const heim_oid
*key_oid
,
1282 hx509_private_key
*private_key
)
1284 struct hx509_private_key_ops
*ops
;
1287 *private_key
= NULL
;
1289 ops
= find_private_alg(key_oid
);
1291 hx509_clear_error_string(context
);
1292 return HX509_SIG_ALG_NO_SUPPORTED
;
1295 ret
= _hx509_private_key_init(private_key
, ops
, NULL
);
1297 hx509_set_error_string(context
, 0, ret
, "out of memory");
1301 ret
= (*ops
->import
)(context
, data
, len
, *private_key
);
1303 _hx509_private_key_free(private_key
);
1313 _hx509_private_key2SPKI(hx509_context context
,
1314 hx509_private_key private_key
,
1315 SubjectPublicKeyInfo
*spki
)
1317 const struct hx509_private_key_ops
*ops
= private_key
->ops
;
1318 if (ops
== NULL
|| ops
->get_spki
== NULL
) {
1319 hx509_set_error_string(context
, 0, HX509_UNIMPLEMENTED_OPERATION
,
1320 "Private key have no key2SPKI function");
1321 return HX509_UNIMPLEMENTED_OPERATION
;
1323 return (*ops
->get_spki
)(context
, private_key
, spki
);
1327 _hx509_generate_private_key_init(hx509_context context
,
1328 const heim_oid
*oid
,
1329 struct hx509_generate_private_context
**ctx
)
1333 if (der_heim_oid_cmp(oid
, oid_id_pkcs1_rsaEncryption()) != 0) {
1334 hx509_set_error_string(context
, 0, EINVAL
,
1335 "private key not an RSA key");
1339 *ctx
= calloc(1, sizeof(**ctx
));
1341 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
1344 (*ctx
)->key_oid
= oid
;
1350 _hx509_generate_private_key_is_ca(hx509_context context
,
1351 struct hx509_generate_private_context
*ctx
)
1358 _hx509_generate_private_key_bits(hx509_context context
,
1359 struct hx509_generate_private_context
*ctx
,
1362 ctx
->num_bits
= bits
;
1368 _hx509_generate_private_key_free(struct hx509_generate_private_context
**ctx
)
1375 _hx509_generate_private_key(hx509_context context
,
1376 struct hx509_generate_private_context
*ctx
,
1377 hx509_private_key
*private_key
)
1379 struct hx509_private_key_ops
*ops
;
1382 *private_key
= NULL
;
1384 ops
= find_private_alg(ctx
->key_oid
);
1386 hx509_clear_error_string(context
);
1387 return HX509_SIG_ALG_NO_SUPPORTED
;
1390 ret
= _hx509_private_key_init(private_key
, ops
, NULL
);
1392 hx509_set_error_string(context
, 0, ret
, "out of memory");
1396 ret
= (*ops
->generate_private_key
)(context
, ctx
, *private_key
);
1398 _hx509_private_key_free(private_key
);
1408 static const heim_octet_string null_entry_oid
= { 2, rk_UNCONST("\x05\x00") };
1410 static const unsigned sha512_oid_tree
[] = { 2, 16, 840, 1, 101, 3, 4, 2, 3 };
1411 const AlgorithmIdentifier _hx509_signature_sha512_data
= {
1412 { 9, rk_UNCONST(sha512_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1415 static const unsigned sha384_oid_tree
[] = { 2, 16, 840, 1, 101, 3, 4, 2, 2 };
1416 const AlgorithmIdentifier _hx509_signature_sha384_data
= {
1417 { 9, rk_UNCONST(sha384_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1420 static const unsigned sha256_oid_tree
[] = { 2, 16, 840, 1, 101, 3, 4, 2, 1 };
1421 const AlgorithmIdentifier _hx509_signature_sha256_data
= {
1422 { 9, rk_UNCONST(sha256_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1425 static const unsigned sha1_oid_tree
[] = { 1, 3, 14, 3, 2, 26 };
1426 const AlgorithmIdentifier _hx509_signature_sha1_data
= {
1427 { 6, rk_UNCONST(sha1_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1430 static const unsigned md5_oid_tree
[] = { 1, 2, 840, 113549, 2, 5 };
1431 const AlgorithmIdentifier _hx509_signature_md5_data
= {
1432 { 6, rk_UNCONST(md5_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1435 static const unsigned md2_oid_tree
[] = { 1, 2, 840, 113549, 2, 2 };
1436 const AlgorithmIdentifier _hx509_signature_md2_data
= {
1437 { 6, rk_UNCONST(md2_oid_tree
) }, rk_UNCONST(&null_entry_oid
)
1440 static const unsigned rsa_with_sha512_oid
[] ={ 1, 2, 840, 113549, 1, 1, 13 };
1441 const AlgorithmIdentifier _hx509_signature_rsa_with_sha512_data
= {
1442 { 7, rk_UNCONST(rsa_with_sha512_oid
) }, NULL
1445 static const unsigned rsa_with_sha384_oid
[] ={ 1, 2, 840, 113549, 1, 1, 12 };
1446 const AlgorithmIdentifier _hx509_signature_rsa_with_sha384_data
= {
1447 { 7, rk_UNCONST(rsa_with_sha384_oid
) }, NULL
1450 static const unsigned rsa_with_sha256_oid
[] ={ 1, 2, 840, 113549, 1, 1, 11 };
1451 const AlgorithmIdentifier _hx509_signature_rsa_with_sha256_data
= {
1452 { 7, rk_UNCONST(rsa_with_sha256_oid
) }, NULL
1455 static const unsigned rsa_with_sha1_oid
[] ={ 1, 2, 840, 113549, 1, 1, 5 };
1456 const AlgorithmIdentifier _hx509_signature_rsa_with_sha1_data
= {
1457 { 7, rk_UNCONST(rsa_with_sha1_oid
) }, NULL
1460 static const unsigned rsa_with_md5_oid
[] ={ 1, 2, 840, 113549, 1, 1, 4 };
1461 const AlgorithmIdentifier _hx509_signature_rsa_with_md5_data
= {
1462 { 7, rk_UNCONST(rsa_with_md5_oid
) }, NULL
1465 static const unsigned rsa_with_md2_oid
[] ={ 1, 2, 840, 113549, 1, 1, 2 };
1466 const AlgorithmIdentifier _hx509_signature_rsa_with_md2_data
= {
1467 { 7, rk_UNCONST(rsa_with_md2_oid
) }, NULL
1470 static const unsigned rsa_oid
[] ={ 1, 2, 840, 113549, 1, 1, 1 };
1471 const AlgorithmIdentifier _hx509_signature_rsa_data
= {
1472 { 7, rk_UNCONST(rsa_oid
) }, NULL
1475 static const unsigned rsa_pkcs1_x509_oid
[] ={ 1, 2, 752, 43, 16, 1 };
1476 const AlgorithmIdentifier _hx509_signature_rsa_pkcs1_x509_data
= {
1477 { 6, rk_UNCONST(rsa_pkcs1_x509_oid
) }, NULL
1480 static const unsigned des_rsdi_ede3_cbc_oid
[] ={ 1, 2, 840, 113549, 3, 7 };
1481 const AlgorithmIdentifier _hx509_des_rsdi_ede3_cbc_oid
= {
1482 { 6, rk_UNCONST(des_rsdi_ede3_cbc_oid
) }, NULL
1485 static const unsigned aes128_cbc_oid
[] ={ 2, 16, 840, 1, 101, 3, 4, 1, 2 };
1486 const AlgorithmIdentifier _hx509_crypto_aes128_cbc_data
= {
1487 { 9, rk_UNCONST(aes128_cbc_oid
) }, NULL
1490 static const unsigned aes256_cbc_oid
[] ={ 2, 16, 840, 1, 101, 3, 4, 1, 42 };
1491 const AlgorithmIdentifier _hx509_crypto_aes256_cbc_data
= {
1492 { 9, rk_UNCONST(aes256_cbc_oid
) }, NULL
1495 const AlgorithmIdentifier
*
1496 hx509_signature_sha512(void)
1497 { return &_hx509_signature_sha512_data
; }
1499 const AlgorithmIdentifier
*
1500 hx509_signature_sha384(void)
1501 { return &_hx509_signature_sha384_data
; }
1503 const AlgorithmIdentifier
*
1504 hx509_signature_sha256(void)
1505 { return &_hx509_signature_sha256_data
; }
1507 const AlgorithmIdentifier
*
1508 hx509_signature_sha1(void)
1509 { return &_hx509_signature_sha1_data
; }
1511 const AlgorithmIdentifier
*
1512 hx509_signature_md5(void)
1513 { return &_hx509_signature_md5_data
; }
1515 const AlgorithmIdentifier
*
1516 hx509_signature_md2(void)
1517 { return &_hx509_signature_md2_data
; }
1519 const AlgorithmIdentifier
*
1520 hx509_signature_rsa_with_sha512(void)
1521 { return &_hx509_signature_rsa_with_sha512_data
; }
1523 const AlgorithmIdentifier
*
1524 hx509_signature_rsa_with_sha384(void)
1525 { return &_hx509_signature_rsa_with_sha384_data
; }
1527 const AlgorithmIdentifier
*
1528 hx509_signature_rsa_with_sha256(void)
1529 { return &_hx509_signature_rsa_with_sha256_data
; }
1531 const AlgorithmIdentifier
*
1532 hx509_signature_rsa_with_sha1(void)
1533 { return &_hx509_signature_rsa_with_sha1_data
; }
1535 const AlgorithmIdentifier
*
1536 hx509_signature_rsa_with_md5(void)
1537 { return &_hx509_signature_rsa_with_md5_data
; }
1539 const AlgorithmIdentifier
*
1540 hx509_signature_rsa_with_md2(void)
1541 { return &_hx509_signature_rsa_with_md2_data
; }
1543 const AlgorithmIdentifier
*
1544 hx509_signature_rsa(void)
1545 { return &_hx509_signature_rsa_data
; }
1547 const AlgorithmIdentifier
*
1548 hx509_signature_rsa_pkcs1_x509(void)
1549 { return &_hx509_signature_rsa_pkcs1_x509_data
; }
1551 const AlgorithmIdentifier
*
1552 hx509_crypto_des_rsdi_ede3_cbc(void)
1553 { return &_hx509_des_rsdi_ede3_cbc_oid
; }
1555 const AlgorithmIdentifier
*
1556 hx509_crypto_aes128_cbc(void)
1557 { return &_hx509_crypto_aes128_cbc_data
; }
1559 const AlgorithmIdentifier
*
1560 hx509_crypto_aes256_cbc(void)
1561 { return &_hx509_crypto_aes256_cbc_data
; }
1567 const AlgorithmIdentifier
* _hx509_crypto_default_sig_alg
=
1568 &_hx509_signature_rsa_with_sha1_data
;
1569 const AlgorithmIdentifier
* _hx509_crypto_default_digest_alg
=
1570 &_hx509_signature_sha1_data
;
1571 const AlgorithmIdentifier
* _hx509_crypto_default_secret_alg
=
1572 &_hx509_crypto_aes128_cbc_data
;
1579 _hx509_private_key_init(hx509_private_key
*key
,
1580 hx509_private_key_ops
*ops
,
1583 *key
= calloc(1, sizeof(**key
));
1588 (*key
)->private_key
.keydata
= keydata
;
1593 _hx509_private_key_ref(hx509_private_key key
)
1596 _hx509_abort("key refcount <= 0 on ref");
1598 if (key
->ref
== UINT_MAX
)
1599 _hx509_abort("key refcount == UINT_MAX on ref");
1604 _hx509_private_pem_name(hx509_private_key key
)
1606 return key
->ops
->pemtype
;
1610 _hx509_private_key_free(hx509_private_key
*key
)
1612 if (key
== NULL
|| *key
== NULL
)
1615 if ((*key
)->ref
== 0)
1616 _hx509_abort("key refcount == 0 on free");
1617 if (--(*key
)->ref
> 0)
1620 if ((*key
)->private_key
.rsa
)
1621 RSA_free((*key
)->private_key
.rsa
);
1622 (*key
)->private_key
.rsa
= NULL
;
1629 _hx509_private_key_assign_rsa(hx509_private_key key
, void *ptr
)
1631 if (key
->private_key
.rsa
)
1632 RSA_free(key
->private_key
.rsa
);
1633 key
->private_key
.rsa
= ptr
;
1634 key
->signature_alg
= oid_id_pkcs1_sha1WithRSAEncryption();
1635 key
->md
= &pkcs1_rsa_sha1_alg
;
1639 _hx509_private_key_oid(hx509_context context
,
1640 const hx509_private_key key
,
1644 ret
= der_copy_oid((*key
->ops
->key_oid
)(), data
);
1646 hx509_set_error_string(context
, 0, ret
, "malloc out of memory");
1651 _hx509_private_key_exportable(hx509_private_key key
)
1653 if (key
->ops
->export
== NULL
)
1659 _hx509_private_key_get_internal(hx509_context context
,
1660 hx509_private_key key
,
1663 if (key
->ops
->get_internal
== NULL
)
1665 return (*key
->ops
->get_internal
)(context
, key
, type
);
1669 _hx509_private_key_export(hx509_context context
,
1670 const hx509_private_key key
,
1671 heim_octet_string
*data
)
1673 if (key
->ops
->export
== NULL
) {
1674 hx509_clear_error_string(context
);
1675 return HX509_UNIMPLEMENTED_OPERATION
;
1677 return (*key
->ops
->export
)(context
, key
, data
);
1684 struct hx509cipher
{
1686 const heim_oid
*(*oid_func
)(void);
1687 const AlgorithmIdentifier
*(*ai_func
)(void);
1688 const EVP_CIPHER
*(*evp_func
)(void);
1689 int (*get_params
)(hx509_context
, const hx509_crypto
,
1690 const heim_octet_string
*, heim_octet_string
*);
1691 int (*set_params
)(hx509_context
, const heim_octet_string
*,
1692 hx509_crypto
, heim_octet_string
*);
1695 struct hx509_crypto_data
{
1697 const struct hx509cipher
*cipher
;
1698 const EVP_CIPHER
*c
;
1699 heim_octet_string key
;
1708 static const heim_oid
*
1709 oid_private_rc2_40(void)
1711 static unsigned oid_data
[] = { 127, 1 };
1712 static const heim_oid oid
= { 2, oid_data
};
1723 CMSCBCParam_get(hx509_context context
, const hx509_crypto crypto
,
1724 const heim_octet_string
*ivec
, heim_octet_string
*param
)
1729 assert(crypto
->param
== NULL
);
1733 ASN1_MALLOC_ENCODE(CMSCBCParameter
, param
->data
, param
->length
,
1735 if (ret
== 0 && size
!= param
->length
)
1736 _hx509_abort("Internal asn1 encoder failure");
1738 hx509_clear_error_string(context
);
1743 CMSCBCParam_set(hx509_context context
, const heim_octet_string
*param
,
1744 hx509_crypto crypto
, heim_octet_string
*ivec
)
1750 ret
= decode_CMSCBCParameter(param
->data
, param
->length
, ivec
, NULL
);
1752 hx509_clear_error_string(context
);
1757 struct _RC2_params
{
1758 int maximum_effective_key
;
1762 CMSRC2CBCParam_get(hx509_context context
, const hx509_crypto crypto
,
1763 const heim_octet_string
*ivec
, heim_octet_string
*param
)
1765 CMSRC2CBCParameter rc2params
;
1766 const struct _RC2_params
*p
= crypto
->param
;
1767 int maximum_effective_key
= 128;
1771 memset(&rc2params
, 0, sizeof(rc2params
));
1774 maximum_effective_key
= p
->maximum_effective_key
;
1776 switch(maximum_effective_key
) {
1778 rc2params
.rc2ParameterVersion
= 160;
1781 rc2params
.rc2ParameterVersion
= 120;
1784 rc2params
.rc2ParameterVersion
= 58;
1787 rc2params
.iv
= *ivec
;
1789 ASN1_MALLOC_ENCODE(CMSRC2CBCParameter
, param
->data
, param
->length
,
1790 &rc2params
, &size
, ret
);
1791 if (ret
== 0 && size
!= param
->length
)
1792 _hx509_abort("Internal asn1 encoder failure");
1798 CMSRC2CBCParam_set(hx509_context context
, const heim_octet_string
*param
,
1799 hx509_crypto crypto
, heim_octet_string
*ivec
)
1801 CMSRC2CBCParameter rc2param
;
1802 struct _RC2_params
*p
;
1806 ret
= decode_CMSRC2CBCParameter(param
->data
, param
->length
,
1809 hx509_clear_error_string(context
);
1813 p
= calloc(1, sizeof(*p
));
1815 free_CMSRC2CBCParameter(&rc2param
);
1816 hx509_clear_error_string(context
);
1819 switch(rc2param
.rc2ParameterVersion
) {
1821 crypto
->c
= EVP_rc2_40_cbc();
1822 p
->maximum_effective_key
= 40;
1825 crypto
->c
= EVP_rc2_64_cbc();
1826 p
->maximum_effective_key
= 64;
1829 crypto
->c
= EVP_rc2_cbc();
1830 p
->maximum_effective_key
= 128;
1834 free_CMSRC2CBCParameter(&rc2param
);
1835 return HX509_CRYPTO_SIG_INVALID_FORMAT
;
1838 ret
= der_copy_octet_string(&rc2param
.iv
, ivec
);
1839 free_CMSRC2CBCParameter(&rc2param
);
1842 hx509_clear_error_string(context
);
1853 static const struct hx509cipher ciphers
[] = {
1856 oid_id_pkcs3_rc2_cbc
,
1864 oid_id_rsadsi_rc2_cbc
,
1880 oid_id_pkcs3_des_ede3_cbc
,
1888 oid_id_rsadsi_des_ede3_cbc
,
1889 hx509_crypto_des_rsdi_ede3_cbc
,
1897 hx509_crypto_aes128_cbc
,
1913 hx509_crypto_aes256_cbc
,
1920 static const struct hx509cipher
*
1921 find_cipher_by_oid(const heim_oid
*oid
)
1925 for (i
= 0; i
< sizeof(ciphers
)/sizeof(ciphers
[0]); i
++)
1926 if (der_heim_oid_cmp(oid
, (*ciphers
[i
].oid_func
)()) == 0)
1932 static const struct hx509cipher
*
1933 find_cipher_by_name(const char *name
)
1937 for (i
= 0; i
< sizeof(ciphers
)/sizeof(ciphers
[0]); i
++)
1938 if (strcasecmp(name
, ciphers
[i
].name
) == 0)
1946 hx509_crypto_enctype_by_name(const char *name
)
1948 const struct hx509cipher
*cipher
;
1950 cipher
= find_cipher_by_name(name
);
1953 return (*cipher
->oid_func
)();
1957 hx509_crypto_init(hx509_context context
,
1958 const char *provider
,
1959 const heim_oid
*enctype
,
1960 hx509_crypto
*crypto
)
1962 const struct hx509cipher
*cipher
;
1966 cipher
= find_cipher_by_oid(enctype
);
1967 if (cipher
== NULL
) {
1968 hx509_set_error_string(context
, 0, HX509_ALG_NOT_SUPP
,
1969 "Algorithm not supported");
1970 return HX509_ALG_NOT_SUPP
;
1973 *crypto
= calloc(1, sizeof(**crypto
));
1974 if (*crypto
== NULL
) {
1975 hx509_clear_error_string(context
);
1979 (*crypto
)->cipher
= cipher
;
1980 (*crypto
)->c
= (*cipher
->evp_func
)();
1982 if (der_copy_oid(enctype
, &(*crypto
)->oid
)) {
1983 hx509_crypto_destroy(*crypto
);
1985 hx509_clear_error_string(context
);
1993 hx509_crypto_provider(hx509_crypto crypto
)
1999 hx509_crypto_destroy(hx509_crypto crypto
)
2003 if (crypto
->key
.data
)
2004 free(crypto
->key
.data
);
2006 free(crypto
->param
);
2007 der_free_oid(&crypto
->oid
);
2008 memset(crypto
, 0, sizeof(*crypto
));
2013 hx509_crypto_set_key_name(hx509_crypto crypto
, const char *name
)
2019 hx509_crypto_set_key_data(hx509_crypto crypto
, const void *data
, size_t length
)
2021 if (EVP_CIPHER_key_length(crypto
->c
) > length
)
2022 return HX509_CRYPTO_INTERNAL_ERROR
;
2024 if (crypto
->key
.data
) {
2025 free(crypto
->key
.data
);
2026 crypto
->key
.data
= NULL
;
2027 crypto
->key
.length
= 0;
2029 crypto
->key
.data
= malloc(length
);
2030 if (crypto
->key
.data
== NULL
)
2032 memcpy(crypto
->key
.data
, data
, length
);
2033 crypto
->key
.length
= length
;
2039 hx509_crypto_set_random_key(hx509_crypto crypto
, heim_octet_string
*key
)
2041 if (crypto
->key
.data
) {
2042 free(crypto
->key
.data
);
2043 crypto
->key
.length
= 0;
2046 crypto
->key
.length
= EVP_CIPHER_key_length(crypto
->c
);
2047 crypto
->key
.data
= malloc(crypto
->key
.length
);
2048 if (crypto
->key
.data
== NULL
) {
2049 crypto
->key
.length
= 0;
2052 if (RAND_bytes(crypto
->key
.data
, crypto
->key
.length
) <= 0) {
2053 free(crypto
->key
.data
);
2054 crypto
->key
.data
= NULL
;
2055 crypto
->key
.length
= 0;
2056 return HX509_CRYPTO_INTERNAL_ERROR
;
2059 return der_copy_octet_string(&crypto
->key
, key
);
2065 hx509_crypto_set_params(hx509_context context
,
2066 hx509_crypto crypto
,
2067 const heim_octet_string
*param
,
2068 heim_octet_string
*ivec
)
2070 return (*crypto
->cipher
->set_params
)(context
, param
, crypto
, ivec
);
2074 hx509_crypto_get_params(hx509_context context
,
2075 hx509_crypto crypto
,
2076 const heim_octet_string
*ivec
,
2077 heim_octet_string
*param
)
2079 return (*crypto
->cipher
->get_params
)(context
, crypto
, ivec
, param
);
2083 hx509_crypto_random_iv(hx509_crypto crypto
, heim_octet_string
*ivec
)
2085 ivec
->length
= EVP_CIPHER_iv_length(crypto
->c
);
2086 ivec
->data
= malloc(ivec
->length
);
2087 if (ivec
->data
== NULL
) {
2092 if (RAND_bytes(ivec
->data
, ivec
->length
) <= 0) {
2096 return HX509_CRYPTO_INTERNAL_ERROR
;
2102 hx509_crypto_encrypt(hx509_crypto crypto
,
2104 const size_t length
,
2105 const heim_octet_string
*ivec
,
2106 heim_octet_string
**ciphertext
)
2114 assert(EVP_CIPHER_iv_length(crypto
->c
) == ivec
->length
);
2116 EVP_CIPHER_CTX_init(&evp
);
2118 ret
= EVP_CipherInit_ex(&evp
, crypto
->c
, NULL
,
2119 crypto
->key
.data
, ivec
->data
, 1);
2121 EVP_CIPHER_CTX_cleanup(&evp
);
2122 ret
= HX509_CRYPTO_INTERNAL_ERROR
;
2126 *ciphertext
= calloc(1, sizeof(**ciphertext
));
2127 if (*ciphertext
== NULL
) {
2132 if (EVP_CIPHER_block_size(crypto
->c
) == 1) {
2135 int bsize
= EVP_CIPHER_block_size(crypto
->c
);
2136 padsize
= bsize
- (length
% bsize
);
2138 (*ciphertext
)->length
= length
+ padsize
;
2139 (*ciphertext
)->data
= malloc(length
+ padsize
);
2140 if ((*ciphertext
)->data
== NULL
) {
2145 memcpy((*ciphertext
)->data
, data
, length
);
2148 unsigned char *p
= (*ciphertext
)->data
;
2150 for (i
= 0; i
< padsize
; i
++)
2154 ret
= EVP_Cipher(&evp
, (*ciphertext
)->data
,
2155 (*ciphertext
)->data
,
2158 ret
= HX509_CRYPTO_INTERNAL_ERROR
;
2166 if ((*ciphertext
)->data
) {
2167 free((*ciphertext
)->data
);
2173 EVP_CIPHER_CTX_cleanup(&evp
);
2179 hx509_crypto_decrypt(hx509_crypto crypto
,
2181 const size_t length
,
2182 heim_octet_string
*ivec
,
2183 heim_octet_string
*clear
)
2192 if (ivec
&& EVP_CIPHER_iv_length(crypto
->c
) < ivec
->length
)
2193 return HX509_CRYPTO_INTERNAL_ERROR
;
2195 if (crypto
->key
.data
== NULL
)
2196 return HX509_CRYPTO_INTERNAL_ERROR
;
2201 EVP_CIPHER_CTX_init(&evp
);
2203 ret
= EVP_CipherInit_ex(&evp
, crypto
->c
, NULL
,
2204 crypto
->key
.data
, idata
, 0);
2206 EVP_CIPHER_CTX_cleanup(&evp
);
2207 return HX509_CRYPTO_INTERNAL_ERROR
;
2210 clear
->length
= length
;
2211 clear
->data
= malloc(length
);
2212 if (clear
->data
== NULL
) {
2213 EVP_CIPHER_CTX_cleanup(&evp
);
2218 if (EVP_Cipher(&evp
, clear
->data
, data
, length
) != 1) {
2219 return HX509_CRYPTO_INTERNAL_ERROR
;
2221 EVP_CIPHER_CTX_cleanup(&evp
);
2223 if (EVP_CIPHER_block_size(crypto
->c
) > 1) {
2226 int j
, bsize
= EVP_CIPHER_block_size(crypto
->c
);
2228 if (clear
->length
< bsize
) {
2229 ret
= HX509_CMS_PADDING_ERROR
;
2234 p
+= clear
->length
- 1;
2236 if (padsize
> bsize
) {
2237 ret
= HX509_CMS_PADDING_ERROR
;
2240 clear
->length
-= padsize
;
2241 for (j
= 0; j
< padsize
; j
++) {
2242 if (*p
-- != padsize
) {
2243 ret
= HX509_CMS_PADDING_ERROR
;
2259 typedef int (*PBE_string2key_func
)(hx509_context
,
2261 const heim_octet_string
*,
2262 hx509_crypto
*, heim_octet_string
*,
2263 heim_octet_string
*,
2264 const heim_oid
*, const EVP_MD
*);
2267 PBE_string2key(hx509_context context
,
2268 const char *password
,
2269 const heim_octet_string
*parameters
,
2270 hx509_crypto
*crypto
,
2271 heim_octet_string
*key
, heim_octet_string
*iv
,
2272 const heim_oid
*enc_oid
,
2275 PKCS12_PBEParams p12params
;
2278 int iter
, saltlen
, ret
;
2279 unsigned char *salt
;
2281 passwordlen
= password
? strlen(password
) : 0;
2283 if (parameters
== NULL
)
2284 return HX509_ALG_NOT_SUPP
;
2286 ret
= decode_PKCS12_PBEParams(parameters
->data
,
2292 if (p12params
.iterations
)
2293 iter
= *p12params
.iterations
;
2296 salt
= p12params
.salt
.data
;
2297 saltlen
= p12params
.salt
.length
;
2299 if (!PKCS12_key_gen (password
, passwordlen
, salt
, saltlen
,
2300 PKCS12_KEY_ID
, iter
, key
->length
, key
->data
, md
)) {
2301 ret
= HX509_CRYPTO_INTERNAL_ERROR
;
2305 if (!PKCS12_key_gen (password
, passwordlen
, salt
, saltlen
,
2306 PKCS12_IV_ID
, iter
, iv
->length
, iv
->data
, md
)) {
2307 ret
= HX509_CRYPTO_INTERNAL_ERROR
;
2311 ret
= hx509_crypto_init(context
, NULL
, enc_oid
, &c
);
2315 ret
= hx509_crypto_set_key_data(c
, key
->data
, key
->length
);
2317 hx509_crypto_destroy(c
);
2323 free_PKCS12_PBEParams(&p12params
);
2327 static const heim_oid
*
2328 find_string2key(const heim_oid
*oid
,
2329 const EVP_CIPHER
**c
,
2331 PBE_string2key_func
*s2k
)
2333 if (der_heim_oid_cmp(oid
, oid_id_pbewithSHAAnd40BitRC2_CBC()) == 0) {
2334 *c
= EVP_rc2_40_cbc();
2336 *s2k
= PBE_string2key
;
2337 return oid_private_rc2_40();
2338 } else if (der_heim_oid_cmp(oid
, oid_id_pbeWithSHAAnd128BitRC2_CBC()) == 0) {
2341 *s2k
= PBE_string2key
;
2342 return oid_id_pkcs3_rc2_cbc();
2344 } else if (der_heim_oid_cmp(oid
, oid_id_pbeWithSHAAnd40BitRC4()) == 0) {
2347 *s2k
= PBE_string2key
;
2349 } else if (der_heim_oid_cmp(oid
, oid_id_pbeWithSHAAnd128BitRC4()) == 0) {
2352 *s2k
= PBE_string2key
;
2353 return oid_id_pkcs3_rc4();
2355 } else if (der_heim_oid_cmp(oid
, oid_id_pbeWithSHAAnd3_KeyTripleDES_CBC()) == 0) {
2356 *c
= EVP_des_ede3_cbc();
2358 *s2k
= PBE_string2key
;
2359 return oid_id_pkcs3_des_ede3_cbc();
2370 _hx509_pbe_encrypt(hx509_context context
,
2372 const AlgorithmIdentifier
*ai
,
2373 const heim_octet_string
*content
,
2374 heim_octet_string
*econtent
)
2376 hx509_clear_error_string(context
);
2385 _hx509_pbe_decrypt(hx509_context context
,
2387 const AlgorithmIdentifier
*ai
,
2388 const heim_octet_string
*econtent
,
2389 heim_octet_string
*content
)
2391 const struct _hx509_password
*pw
;
2392 heim_octet_string key
, iv
;
2393 const heim_oid
*enc_oid
;
2394 const EVP_CIPHER
*c
;
2396 PBE_string2key_func s2k
;
2399 memset(&key
, 0, sizeof(key
));
2400 memset(&iv
, 0, sizeof(iv
));
2402 memset(content
, 0, sizeof(*content
));
2404 enc_oid
= find_string2key(&ai
->algorithm
, &c
, &md
, &s2k
);
2405 if (enc_oid
== NULL
) {
2406 hx509_set_error_string(context
, 0, HX509_ALG_NOT_SUPP
,
2407 "String to key algorithm not supported");
2408 ret
= HX509_ALG_NOT_SUPP
;
2412 key
.length
= EVP_CIPHER_key_length(c
);
2413 key
.data
= malloc(key
.length
);
2414 if (key
.data
== NULL
) {
2416 hx509_clear_error_string(context
);
2420 iv
.length
= EVP_CIPHER_iv_length(c
);
2421 iv
.data
= malloc(iv
.length
);
2422 if (iv
.data
== NULL
) {
2424 hx509_clear_error_string(context
);
2428 pw
= _hx509_lock_get_passwords(lock
);
2430 ret
= HX509_CRYPTO_INTERNAL_ERROR
;
2431 for (i
= 0; i
< pw
->len
+ 1; i
++) {
2432 hx509_crypto crypto
;
2433 const char *password
;
2436 password
= pw
->val
[i
];
2437 else if (i
< pw
->len
+ 1)
2442 ret
= (*s2k
)(context
, password
, ai
->parameters
, &crypto
,
2443 &key
, &iv
, enc_oid
, md
);
2447 ret
= hx509_crypto_decrypt(crypto
,
2452 hx509_crypto_destroy(crypto
);
2459 der_free_octet_string(&key
);
2461 der_free_octet_string(&iv
);
2471 _hx509_match_keys(hx509_cert c
, hx509_private_key private_key
)
2473 const Certificate
*cert
;
2474 const SubjectPublicKeyInfo
*spi
;
2480 if (private_key
->private_key
.rsa
== NULL
)
2483 rsa
= private_key
->private_key
.rsa
;
2484 if (rsa
->d
== NULL
|| rsa
->p
== NULL
|| rsa
->q
== NULL
)
2487 cert
= _hx509_get_cert(c
);
2488 spi
= &cert
->tbsCertificate
.subjectPublicKeyInfo
;
2494 ret
= decode_RSAPublicKey(spi
->subjectPublicKey
.data
,
2495 spi
->subjectPublicKey
.length
/ 8,
2501 rsa
->n
= heim_int2BN(&pk
.modulus
);
2502 rsa
->e
= heim_int2BN(&pk
.publicExponent
);
2504 free_RSAPublicKey(&pk
);
2506 rsa
->d
= BN_dup(private_key
->private_key
.rsa
->d
);
2507 rsa
->p
= BN_dup(private_key
->private_key
.rsa
->p
);
2508 rsa
->q
= BN_dup(private_key
->private_key
.rsa
->q
);
2509 rsa
->dmp1
= BN_dup(private_key
->private_key
.rsa
->dmp1
);
2510 rsa
->dmq1
= BN_dup(private_key
->private_key
.rsa
->dmq1
);
2511 rsa
->iqmp
= BN_dup(private_key
->private_key
.rsa
->iqmp
);
2513 if (rsa
->n
== NULL
|| rsa
->e
== NULL
||
2514 rsa
->d
== NULL
|| rsa
->p
== NULL
|| rsa
->q
== NULL
||
2515 rsa
->dmp1
== NULL
|| rsa
->dmq1
== NULL
) {
2520 ret
= RSA_check_key(rsa
);
2526 static const heim_oid
*
2527 find_keytype(const hx509_private_key key
)
2529 const struct signature_alg
*md
;
2534 md
= find_sig_alg(key
->signature_alg
);
2537 return (*md
->key_oid
)();
2542 hx509_crypto_select(const hx509_context context
,
2544 const hx509_private_key source
,
2545 hx509_peer_info peer
,
2546 AlgorithmIdentifier
*selected
)
2548 const AlgorithmIdentifier
*def
;
2552 memset(selected
, 0, sizeof(*selected
));
2554 if (type
== HX509_SELECT_DIGEST
) {
2556 def
= _hx509_crypto_default_digest_alg
;
2557 } else if (type
== HX509_SELECT_PUBLIC_SIG
) {
2558 bits
= SIG_PUBLIC_SIG
;
2559 /* XXX depend on `source´ and `peer´ */
2560 def
= _hx509_crypto_default_sig_alg
;
2561 } else if (type
== HX509_SELECT_SECRET_ENC
) {
2563 def
= _hx509_crypto_default_secret_alg
;
2565 hx509_set_error_string(context
, 0, EINVAL
,
2566 "Unknown type %d of selection", type
);
2571 const heim_oid
*keytype
= NULL
;
2573 keytype
= find_keytype(source
);
2575 for (i
= 0; i
< peer
->len
; i
++) {
2576 for (j
= 0; sig_algs
[j
]; j
++) {
2577 if ((sig_algs
[j
]->flags
& bits
) != bits
)
2579 if (der_heim_oid_cmp((*sig_algs
[j
]->sig_oid
)(),
2580 &peer
->val
[i
].algorithm
) != 0)
2582 if (keytype
&& sig_algs
[j
]->key_oid
&&
2583 der_heim_oid_cmp(keytype
, (*sig_algs
[j
]->key_oid
)()))
2586 /* found one, use that */
2587 ret
= copy_AlgorithmIdentifier(&peer
->val
[i
], selected
);
2589 hx509_clear_error_string(context
);
2592 if (bits
& SIG_SECRET
) {
2593 const struct hx509cipher
*cipher
;
2595 cipher
= find_cipher_by_oid(&peer
->val
[i
].algorithm
);
2598 if (cipher
->ai_func
== NULL
)
2600 ret
= copy_AlgorithmIdentifier(cipher
->ai_func(), selected
);
2602 hx509_clear_error_string(context
);
2609 ret
= copy_AlgorithmIdentifier(def
, selected
);
2611 hx509_clear_error_string(context
);
2616 hx509_crypto_available(hx509_context context
,
2619 AlgorithmIdentifier
**val
,
2622 const heim_oid
*keytype
= NULL
;
2623 unsigned int len
, i
;
2629 if (type
== HX509_SELECT_ALL
) {
2630 bits
= SIG_DIGEST
| SIG_PUBLIC_SIG
| SIG_SECRET
;
2631 } else if (type
== HX509_SELECT_DIGEST
) {
2633 } else if (type
== HX509_SELECT_PUBLIC_SIG
) {
2634 bits
= SIG_PUBLIC_SIG
;
2636 hx509_set_error_string(context
, 0, EINVAL
,
2637 "Unknown type %d of available", type
);
2642 keytype
= find_keytype(_hx509_cert_private_key(source
));
2645 for (i
= 0; sig_algs
[i
]; i
++) {
2646 if ((sig_algs
[i
]->flags
& bits
) == 0)
2648 if (sig_algs
[i
]->sig_alg
== NULL
)
2650 if (keytype
&& sig_algs
[i
]->key_oid
&&
2651 der_heim_oid_cmp((*sig_algs
[i
]->key_oid
)(), keytype
))
2654 /* found one, add that to the list */
2655 ptr
= realloc(*val
, sizeof(**val
) * (len
+ 1));
2660 ret
= copy_AlgorithmIdentifier((*sig_algs
[i
]->sig_alg
)(), &(*val
)[len
]);
2667 if (bits
& SIG_SECRET
) {
2669 for (i
= 0; i
< sizeof(ciphers
)/sizeof(ciphers
[0]); i
++) {
2671 if (ciphers
[i
].ai_func
== NULL
)
2674 ptr
= realloc(*val
, sizeof(**val
) * (len
+ 1));
2679 ret
= copy_AlgorithmIdentifier((ciphers
[i
].ai_func
)(), &(*val
)[len
]);
2690 for (i
= 0; i
< len
; i
++)
2691 free_AlgorithmIdentifier(&(*val
)[i
]);
2694 hx509_set_error_string(context
, 0, ENOMEM
, "out of memory");
2699 hx509_crypto_free_algs(AlgorithmIdentifier
*val
,
2703 for (i
= 0; i
< len
; i
++)
2704 free_AlgorithmIdentifier(&val
[i
]);