diff options
Diffstat (limited to 'source4/heimdal/lib/hx509')
-rw-r--r-- | source4/heimdal/lib/hx509/cms.c | 14 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/collector.c | 1 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/crypto.c | 103 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/hx509.h | 8 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/hx509_err.et | 1 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/ks_file.c | 3 | ||||
-rw-r--r-- | source4/heimdal/lib/hx509/ks_p12.c | 1 |
7 files changed, 90 insertions, 41 deletions
diff --git a/source4/heimdal/lib/hx509/cms.c b/source4/heimdal/lib/hx509/cms.c index 224c39086c..ef986fd4ed 100644 --- a/source4/heimdal/lib/hx509/cms.c +++ b/source4/heimdal/lib/hx509/cms.c @@ -532,6 +532,7 @@ out: * @param flags flags to control the behavior. * - HX509_CMS_EV_NO_KU_CHECK - Dont check KU on certificate * - HX509_CMS_EV_ALLOW_WEAK - Allow weak crytpo + * - HX509_CMS_EV_ID_NAME - prefer issuer name and serial number * @param cert Certificate to encrypt the EnvelopedData encryption key * with. * @param data pointer the data to encrypt. @@ -559,9 +560,9 @@ hx509_cms_envelope_1(hx509_context context, heim_octet_string ivec; heim_octet_string key; hx509_crypto crypto = NULL; + int ret, cmsidflag; EnvelopedData ed; size_t size; - int ret; memset(&ivec, 0, sizeof(ivec)); memset(&key, 0, sizeof(key)); @@ -648,8 +649,15 @@ hx509_cms_envelope_1(hx509_context context, ri = &ed.recipientInfos.val[0]; - ri->version = 0; - ret = fill_CMSIdentifier(cert, CMS_ID_SKI, &ri->rid); + if (flags & HX509_CMS_EV_ID_NAME) { + ri->version = 0; + cmsidflag = CMS_ID_NAME; + } else { + ri->version = 2; + cmsidflag = CMS_ID_SKI; + } + + ret = fill_CMSIdentifier(cert, cmsidflag, &ri->rid); if (ret) { hx509_set_error_string(context, 0, ret, "Failed to set CMS identifier info " diff --git a/source4/heimdal/lib/hx509/collector.c b/source4/heimdal/lib/hx509/collector.c index ab36fe2dc8..1a44de00a3 100644 --- a/source4/heimdal/lib/hx509/collector.c +++ b/source4/heimdal/lib/hx509/collector.c @@ -145,6 +145,7 @@ _hx509_collector_private_key_add(hx509_context context, } else { ret = _hx509_parse_private_key(context, alg, key_data->data, key_data->length, + HX509_KEY_FORMAT_DER, &key->private_key); if (ret) goto out; diff --git a/source4/heimdal/lib/hx509/crypto.c b/source4/heimdal/lib/hx509/crypto.c index de7717af02..a38226d94c 100644 --- a/source4/heimdal/lib/hx509/crypto.c +++ b/source4/heimdal/lib/hx509/crypto.c @@ -53,9 +53,11 @@ struct hx509_private_key_ops { SubjectPublicKeyInfo *); int (*export)(hx509_context context, const hx509_private_key, + hx509_key_format_t, heim_octet_string *); int (*import)(hx509_context, const AlgorithmIdentifier *, - const void *, size_t, hx509_private_key); + const void *, size_t, hx509_key_format_t, + hx509_private_key); int (*generate_private_key)(hx509_context, struct hx509_generate_private_context *, hx509_private_key); @@ -750,18 +752,27 @@ rsa_private_key_import(hx509_context context, const AlgorithmIdentifier *keyai, const void *data, size_t len, + hx509_key_format_t format, hx509_private_key private_key) { - const unsigned char *p = data; + switch (format) { + case HX509_KEY_FORMAT_DER: { + const unsigned char *p = data; + + private_key->private_key.rsa = + d2i_RSAPrivateKey(NULL, &p, len); + if (private_key->private_key.rsa == NULL) { + hx509_set_error_string(context, 0, HX509_PARSING_KEY_FAILED, + "Failed to parse RSA key"); + return HX509_PARSING_KEY_FAILED; + } + private_key->signature_alg = ASN1_OID_ID_PKCS1_SHA1WITHRSAENCRYPTION; + break; - private_key->private_key.rsa = - d2i_RSAPrivateKey(NULL, &p, len); - if (private_key->private_key.rsa == NULL) { - hx509_set_error_string(context, 0, HX509_PARSING_KEY_FAILED, - "Failed to parse RSA key"); - return HX509_PARSING_KEY_FAILED; } - private_key->signature_alg = ASN1_OID_ID_PKCS1_SHA1WITHRSAENCRYPTION; + default: + return HX509_CRYPTO_KEY_FORMAT_UNSUPPORTED; + } return 0; } @@ -812,7 +823,7 @@ rsa_generate_private_key(hx509_context context, unsigned long bits; static const int default_rsa_e = 65537; - static const int default_rsa_bits = 1024; + static const int default_rsa_bits = 2048; private_key->private_key.rsa = RSA_new(); if (private_key->private_key.rsa == NULL) { @@ -828,8 +839,6 @@ rsa_generate_private_key(hx509_context context, if (ctx->num_bits) bits = ctx->num_bits; - else if (ctx->isCA) - bits *= 2; ret = RSA_generate_key_ex(private_key->private_key.rsa, bits, e, NULL); BN_free(e); @@ -846,6 +855,7 @@ rsa_generate_private_key(hx509_context context, static int rsa_private_key_export(hx509_context context, const hx509_private_key key, + hx509_key_format_t format, heim_octet_string *data) { int ret; @@ -853,25 +863,32 @@ rsa_private_key_export(hx509_context context, data->data = NULL; data->length = 0; - ret = i2d_RSAPrivateKey(key->private_key.rsa, NULL); - if (ret <= 0) { - ret = EINVAL; - hx509_set_error_string(context, 0, ret, + switch (format) { + case HX509_KEY_FORMAT_DER: + + ret = i2d_RSAPrivateKey(key->private_key.rsa, NULL); + if (ret <= 0) { + ret = EINVAL; + hx509_set_error_string(context, 0, ret, "Private key is not exportable"); - return ret; - } + return ret; + } - data->data = malloc(ret); - if (data->data == NULL) { - ret = ENOMEM; - hx509_set_error_string(context, 0, ret, "malloc out of memory"); - return ret; - } - data->length = ret; + data->data = malloc(ret); + if (data->data == NULL) { + ret = ENOMEM; + hx509_set_error_string(context, 0, ret, "malloc out of memory"); + return ret; + } + data->length = ret; - { - unsigned char *p = data->data; - i2d_RSAPrivateKey(key->private_key.rsa, &p); + { + unsigned char *p = data->data; + i2d_RSAPrivateKey(key->private_key.rsa, &p); + } + break; + default: + return HX509_CRYPTO_KEY_FORMAT_UNSUPPORTED; } return 0; @@ -917,9 +934,10 @@ ecdsa_private_key2SPKI(hx509_context context, static int ecdsa_private_key_export(hx509_context context, const hx509_private_key key, + hx509_key_format_t format, heim_octet_string *data) { - return ENOMEM; + return HX509_CRYPTO_KEY_FORMAT_UNSUPPORTED; } static int @@ -927,6 +945,7 @@ ecdsa_private_key_import(hx509_context context, const AlgorithmIdentifier *keyai, const void *data, size_t len, + hx509_key_format_t format, hx509_private_key private_key) { const unsigned char *p = data; @@ -961,13 +980,21 @@ ecdsa_private_key_import(hx509_context context, pkey = &key; } - private_key->private_key.ecdsa = d2i_ECPrivateKey(pkey, &p, len); - if (private_key->private_key.ecdsa == NULL) { - hx509_set_error_string(context, 0, HX509_PARSING_KEY_FAILED, - "Failed to parse EC private key"); - return HX509_PARSING_KEY_FAILED; + switch (format) { + case HX509_KEY_FORMAT_DER: + + private_key->private_key.ecdsa = d2i_ECPrivateKey(pkey, &p, len); + if (private_key->private_key.ecdsa == NULL) { + hx509_set_error_string(context, 0, HX509_PARSING_KEY_FAILED, + "Failed to parse EC private key"); + return HX509_PARSING_KEY_FAILED; + } + private_key->signature_alg = ASN1_OID_ID_ECDSA_WITH_SHA256; + break; + + default: + return HX509_CRYPTO_KEY_FORMAT_UNSUPPORTED; } - private_key->signature_alg = ASN1_OID_ID_ECDSA_WITH_SHA256; return 0; } @@ -1735,6 +1762,7 @@ _hx509_parse_private_key(hx509_context context, const AlgorithmIdentifier *keyai, const void *data, size_t len, + hx509_key_format_t format, hx509_private_key *private_key) { struct hx509_private_key_ops *ops; @@ -1754,7 +1782,7 @@ _hx509_parse_private_key(hx509_context context, return ret; } - ret = (*ops->import)(context, keyai, data, len, *private_key); + ret = (*ops->import)(context, keyai, data, len, format, *private_key); if (ret) _hx509_private_key_free(private_key); @@ -2047,13 +2075,14 @@ _hx509_private_key_get_internal(hx509_context context, int _hx509_private_key_export(hx509_context context, const hx509_private_key key, + hx509_key_format_t format, heim_octet_string *data) { if (key->ops->export == NULL) { hx509_clear_error_string(context); return HX509_UNIMPLEMENTED_OPERATION; } - return (*key->ops->export)(context, key, data); + return (*key->ops->export)(context, key, format, data); } /* diff --git a/source4/heimdal/lib/hx509/hx509.h b/source4/heimdal/lib/hx509/hx509.h index b6eeac9d18..1a5e2f3080 100644 --- a/source4/heimdal/lib/hx509/hx509.h +++ b/source4/heimdal/lib/hx509/hx509.h @@ -76,6 +76,13 @@ enum { HX509_CRYPTO_PADDING_NONE = 1 }; +enum { + HX509_KEY_FORMAT_GUESS = 0, + HX509_KEY_FORMAT_DER = 1, + HX509_KEY_FORMAT_WIN_BACKUPKEY = 2 +}; +typedef uint32_t hx509_key_format_t; + struct hx509_cert_attribute_data { heim_oid oid; heim_octet_string data; @@ -135,6 +142,7 @@ typedef enum { /* flags to hx509_cms_envelope_1 */ #define HX509_CMS_EV_NO_KU_CHECK 0x01 #define HX509_CMS_EV_ALLOW_WEAK 0x02 +#define HX509_CMS_EV_ID_NAME 0x04 /* flags to hx509_cms_verify_signed */ #define HX509_CMS_VS_ALLOW_DATA_OID_MISMATCH 0x01 diff --git a/source4/heimdal/lib/hx509/hx509_err.et b/source4/heimdal/lib/hx509/hx509_err.et index 76bbfaeaba..6225f125fb 100644 --- a/source4/heimdal/lib/hx509/hx509_err.et +++ b/source4/heimdal/lib/hx509/hx509_err.et @@ -66,6 +66,7 @@ error_code RSA_PRIVATE_ENCRYPT, "RSA private encyption failed" error_code RSA_PUBLIC_DECRYPT, "RSA public decryption failed" error_code RSA_PRIVATE_DECRYPT, "RSA private decryption failed" error_code ALGORITHM_BEST_BEFORE, "Algorithm has passed its best before date" +error_code KEY_FORMAT_UNSUPPORTED, "Key format is unsupported" # revoke related errors index 96 diff --git a/source4/heimdal/lib/hx509/ks_file.c b/source4/heimdal/lib/hx509/ks_file.c index 645dc405a2..ecd3a6edaa 100644 --- a/source4/heimdal/lib/hx509/ks_file.c +++ b/source4/heimdal/lib/hx509/ks_file.c @@ -541,7 +541,8 @@ store_func(hx509_context context, void *ctx, hx509_cert c) free(data.data); if (_hx509_cert_private_key_exportable(c)) { hx509_private_key key = _hx509_cert_private_key(c); - ret = _hx509_private_key_export(context, key, &data); + ret = _hx509_private_key_export(context, key, + HX509_KEY_FORMAT_DER, &data); if (ret) break; hx509_pem_write(context, _hx509_private_pem_name(key), NULL, sc->f, diff --git a/source4/heimdal/lib/hx509/ks_p12.c b/source4/heimdal/lib/hx509/ks_p12.c index d94ab197cd..704cf071d7 100644 --- a/source4/heimdal/lib/hx509/ks_p12.c +++ b/source4/heimdal/lib/hx509/ks_p12.c @@ -535,6 +535,7 @@ store_func(hx509_context context, void *ctx, hx509_cert c) } ret = _hx509_private_key_export(context, _hx509_cert_private_key(c), + HX509_KEY_FORMAT_DER, &pki.privateKey); if (ret) { free_PKCS8PrivateKeyInfo(&pki); |