mirror of https://github.com/openssl/openssl.git
Compare commits
43 Commits
3c44a9c36c
...
b2f53cc922
Author | SHA1 | Date |
---|---|---|
|
b2f53cc922 | |
|
f12f8cc035 | |
|
d0899abb1b | |
|
daa004d484 | |
|
3c4f009959 | |
|
bd1a14bcaf | |
|
8ceae5a622 | |
|
88a1fbb8d1 | |
|
cff8031163 | |
|
758ca8acf0 | |
|
ead653be8b | |
|
dcf009cd89 | |
|
3f633775e4 | |
|
2f41923d2d | |
|
1df3a8a80e | |
|
30740298b6 | |
|
10e26ab122 | |
|
9ccd388664 | |
|
62c4633851 | |
|
707f612416 | |
|
f5fdbb8fff | |
|
6de54753c2 | |
|
133889218e | |
|
2f531a742d | |
|
63e526a4d8 | |
|
1109bc1237 | |
|
e914d23642 | |
|
0afaa27df7 | |
|
deed2379a7 | |
|
09fa39899b | |
|
5e34e6a573 | |
|
082a81404c | |
|
70c05fcde5 | |
|
e348012e99 | |
|
0154dc12a5 | |
|
db6565e5b1 | |
|
707a966f70 | |
|
a4d9183593 | |
|
d4710397a9 | |
|
eb8547c65f | |
|
efee781894 | |
|
849dd3bfad | |
|
b3365c5f9c |
|
@ -75,6 +75,7 @@ providers/common/der/der_rsa_gen.c
|
|||
providers/common/der/der_wrap_gen.c
|
||||
providers/common/der/der_sm2_gen.c
|
||||
providers/common/der/der_ml_dsa_gen.c
|
||||
providers/common/der/der_hkdf_gen.c
|
||||
providers/common/include/prov/der_slh_dsa.h
|
||||
providers/common/include/prov/der_dsa.h
|
||||
providers/common/include/prov/der_ec.h
|
||||
|
@ -84,6 +85,7 @@ providers/common/include/prov/der_digests.h
|
|||
providers/common/include/prov/der_wrap.h
|
||||
providers/common/include/prov/der_sm2.h
|
||||
providers/common/include/prov/der_ml_dsa.h
|
||||
providers/common/include/prov/der_hkdf.h
|
||||
providers/implementations/keymgmt/ml_dsa_kmgmt.c
|
||||
providers/implementations/keymgmt/ml_kem_kmgmt.c
|
||||
providers/implementations/keymgmt/mlx_kmgmt.c
|
||||
|
|
|
@ -145,6 +145,11 @@ OpenSSL 3.6
|
|||
|
||||
*Michael Krueger, Martin Rauch*
|
||||
|
||||
* Added KEMRecipientInfo (RFC 9629) and ML-KEM (draft-ietf-lamps-cms-kyber)
|
||||
support to CMS.
|
||||
|
||||
*Daniel Van Geest (CryptoNext Security)*
|
||||
|
||||
OpenSSL 3.5
|
||||
-----------
|
||||
|
||||
|
|
|
@ -1180,7 +1180,7 @@ generate_buildinfo: generate_doc_buildinfo
|
|||
|
||||
.PHONY: doc-nits md-nits
|
||||
doc-nits: build_generated_pods ## Evaluate OpenSSL documentation
|
||||
$(PERL) $(SRCDIR)/util/find-doc-nits -c -n -l -e -i
|
||||
$(PERL) $(SRCDIR)/util/find-doc-nits -c -n -l -e -i -a
|
||||
|
||||
# This uses "mdl", the markdownlint application, which is written in ruby.
|
||||
# The source is at https://github.com/markdownlint/markdownlint
|
||||
|
|
124
apps/cms.c
124
apps/cms.c
|
@ -53,6 +53,7 @@ static int cms_set_pkey_param(EVP_PKEY_CTX *pctx,
|
|||
static int verify_err = 0;
|
||||
|
||||
typedef struct cms_key_param_st cms_key_param;
|
||||
typedef struct cms_recip_opt_st cms_recip_opt;
|
||||
|
||||
struct cms_key_param_st {
|
||||
int idx;
|
||||
|
@ -60,6 +61,14 @@ struct cms_key_param_st {
|
|||
cms_key_param *next;
|
||||
};
|
||||
|
||||
struct cms_recip_opt_st {
|
||||
int idx;
|
||||
const char *kdf;
|
||||
unsigned char *ukm_data;
|
||||
long ukm_data_length;
|
||||
cms_recip_opt *next;
|
||||
};
|
||||
|
||||
typedef enum OPTION_choice {
|
||||
OPT_COMMON,
|
||||
OPT_INFORM, OPT_OUTFORM, OPT_IN, OPT_OUT, OPT_ENCRYPT,
|
||||
|
@ -85,7 +94,8 @@ typedef enum OPTION_choice {
|
|||
OPT_PROV_ENUM, OPT_CONFIG,
|
||||
OPT_V_ENUM,
|
||||
OPT_CIPHER, OPT_KEKCIPHER,
|
||||
OPT_ORIGINATOR
|
||||
OPT_ORIGINATOR,
|
||||
OPT_RECIP_UKM, OPT_RECIP_KDF
|
||||
} OPTION_CHOICE;
|
||||
|
||||
const OPTIONS cms_options[] = {
|
||||
|
@ -167,13 +177,15 @@ const OPTIONS cms_options[] = {
|
|||
{"kekcipher", OPT_KEKCIPHER, 's',
|
||||
"The key encryption algorithm to use"},
|
||||
{"wrap", OPT_WRAP, 's',
|
||||
"Key wrap algorithm to use when encrypting with key agreement"},
|
||||
"Key wrap algorithm to use when encrypting with key agreement or key encapsulation"},
|
||||
{"aes128-wrap", OPT_AES128_WRAP, '-', "Use AES128 to wrap key"},
|
||||
{"aes192-wrap", OPT_AES192_WRAP, '-', "Use AES192 to wrap key"},
|
||||
{"aes256-wrap", OPT_AES256_WRAP, '-', "Use AES256 to wrap key"},
|
||||
{"des3-wrap", OPT_3DES_WRAP, '-', "Use 3DES-EDE to wrap key"},
|
||||
{"debug_decrypt", OPT_DEBUG_DECRYPT, '-',
|
||||
"Disable MMA protection, return error if no recipient found (see doc)"},
|
||||
{"recip_kdf", OPT_RECIP_KDF, 's', "Set KEMRecipientInfo KDF for current recipient"},
|
||||
{"recip_ukm", OPT_RECIP_UKM, 's', "KEMRecipientInfo user keying material for current recipient, in hex notation"},
|
||||
|
||||
OPT_SECTION("Signing"),
|
||||
{"md", OPT_MD, 's', "Digest algorithm to use"},
|
||||
|
@ -281,6 +293,19 @@ static CMS_ContentInfo *load_content_info(int informat, BIO *in, int flags,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
static cms_recip_opt *alloc_recip_opt(int recipidx)
|
||||
{
|
||||
cms_recip_opt *opt;
|
||||
|
||||
opt = app_malloc(sizeof(*opt), "recipient options buffer");
|
||||
opt->idx = recipidx;
|
||||
opt->next = NULL;
|
||||
opt->kdf = NULL;
|
||||
opt->ukm_data = NULL;
|
||||
opt->ukm_data_length = 0;
|
||||
return opt;
|
||||
}
|
||||
|
||||
int cms_main(int argc, char **argv)
|
||||
{
|
||||
CONF *conf = NULL;
|
||||
|
@ -319,6 +344,8 @@ int cms_main(int argc, char **argv)
|
|||
size_t secret_keylen = 0, secret_keyidlen = 0;
|
||||
unsigned char *pwri_pass = NULL, *pwri_tmp = NULL;
|
||||
unsigned char *secret_key = NULL, *secret_keyid = NULL;
|
||||
cms_recip_opt *recip_first = NULL, *recip_opt = NULL;
|
||||
int recipidx = -1;
|
||||
long ltmp;
|
||||
const char *mime_eol = "\n";
|
||||
OPTION_CHOICE o;
|
||||
|
@ -653,6 +680,46 @@ int cms_main(int argc, char **argv)
|
|||
recipfile = opt_arg();
|
||||
}
|
||||
break;
|
||||
case OPT_RECIP_KDF:
|
||||
case OPT_RECIP_UKM:
|
||||
recipidx = -1;
|
||||
if (operation == SMIME_ENCRYPT) {
|
||||
if (sk_X509_num(encerts) > 0)
|
||||
recipidx += sk_X509_num(encerts);
|
||||
}
|
||||
if (recipidx < 0) {
|
||||
BIO_printf(bio_err, "No recipient specified\n");
|
||||
goto opthelp;
|
||||
}
|
||||
if (recip_opt == NULL || recip_opt->idx != recipidx) {
|
||||
cms_recip_opt *nopt;
|
||||
|
||||
nopt = alloc_recip_opt(recipidx);
|
||||
if (recip_first == NULL)
|
||||
recip_first = nopt;
|
||||
else
|
||||
recip_opt->next = nopt;
|
||||
recip_opt = nopt;
|
||||
}
|
||||
if (o == OPT_RECIP_KDF) {
|
||||
if (recip_opt->kdf != NULL) {
|
||||
BIO_puts(bio_err, "Illegal multiple -recip_kdf for one -recip\n");
|
||||
goto end;
|
||||
}
|
||||
recip_opt->kdf = opt_arg();
|
||||
} else {
|
||||
if (recip_opt->ukm_data != NULL) {
|
||||
BIO_puts(bio_err, "Illegal multiple -recip_ukm for one -recip\n");
|
||||
goto end;
|
||||
}
|
||||
recip_opt->ukm_data = OPENSSL_hexstr2buf(opt_arg(),
|
||||
&recip_opt->ukm_data_length);
|
||||
if (recip_opt->ukm_data == NULL) {
|
||||
BIO_printf(bio_err, "Invalid hex value after -recip_ukm\n");
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case OPT_CIPHER:
|
||||
ciphername = opt_unknown();
|
||||
break;
|
||||
|
@ -831,6 +898,9 @@ int cms_main(int argc, char **argv)
|
|||
if (operation != SMIME_ENCRYPT && *argv != NULL)
|
||||
BIO_printf(bio_err,
|
||||
"Warning: recipient certificate file parameters ignored for operation other than -encrypt\n");
|
||||
if (operation != SMIME_ENCRYPT && recip_first != NULL)
|
||||
BIO_printf(bio_err,
|
||||
"Warning: -recip_kdf and -recip_ukm parameters ignored for operation other than -encrypt\n");
|
||||
|
||||
if ((flags & CMS_BINARY) != 0) {
|
||||
if (!(operation & SMIME_OP))
|
||||
|
@ -990,7 +1060,9 @@ int cms_main(int argc, char **argv)
|
|||
goto end;
|
||||
for (i = 0; i < sk_X509_num(encerts); i++) {
|
||||
CMS_RecipientInfo *ri;
|
||||
int ri_type;
|
||||
cms_key_param *kparam;
|
||||
cms_recip_opt *ropt;
|
||||
int tflags = flags | CMS_KEY_PARAM;
|
||||
/* This flag enforces allocating the EVP_PKEY_CTX for the recipient here */
|
||||
EVP_PKEY_CTX *pctx;
|
||||
|
@ -998,14 +1070,19 @@ int cms_main(int argc, char **argv)
|
|||
int res;
|
||||
|
||||
for (kparam = key_first; kparam; kparam = kparam->next) {
|
||||
if (kparam->idx == i) {
|
||||
if (kparam->idx == i)
|
||||
break;
|
||||
}
|
||||
for (ropt = recip_first; ropt; ropt = ropt->next) {
|
||||
if (ropt->idx == i)
|
||||
break;
|
||||
}
|
||||
ri = CMS_add1_recipient(cms, x, key, originator, tflags);
|
||||
if (ri == NULL)
|
||||
goto end;
|
||||
|
||||
ri_type = CMS_RecipientInfo_type(ri);
|
||||
|
||||
pctx = CMS_RecipientInfo_get0_pkey_ctx(ri);
|
||||
if (pctx != NULL && kparam != NULL) {
|
||||
if (!cms_set_pkey_param(pctx, kparam->param))
|
||||
|
@ -1018,15 +1095,42 @@ int cms_main(int argc, char **argv)
|
|||
if (res <= 0 && res != -2)
|
||||
goto end;
|
||||
|
||||
if (CMS_RecipientInfo_type(ri) == CMS_RECIPINFO_AGREE
|
||||
&& wrap_cipher != NULL) {
|
||||
EVP_CIPHER_CTX *wctx;
|
||||
if (wrap_cipher != NULL) {
|
||||
EVP_CIPHER_CTX *wctx = NULL;
|
||||
|
||||
if (ri_type == CMS_RECIPINFO_AGREE)
|
||||
wctx = CMS_RecipientInfo_kari_get0_ctx(ri);
|
||||
else if (ri_type == CMS_RECIPINFO_KEM)
|
||||
wctx = CMS_RecipientInfo_kemri_get0_ctx(ri);
|
||||
if (wctx != NULL) {
|
||||
if (EVP_EncryptInit_ex(wctx, wrap_cipher, NULL, NULL, NULL) != 1)
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
if (ropt != NULL && ri_type == CMS_RECIPINFO_KEM) {
|
||||
if (ropt->ukm_data != NULL) {
|
||||
if (!CMS_RecipientInfo_kemri_set_ukm(ri, ropt->ukm_data,
|
||||
(int)ropt->ukm_data_length))
|
||||
goto end;
|
||||
}
|
||||
if (ropt->kdf != NULL) {
|
||||
X509_ALGOR *kdf_algo;
|
||||
ASN1_OBJECT *kdf_obj;
|
||||
|
||||
kdf_algo = CMS_RecipientInfo_kemri_get0_kdf_alg(ri);
|
||||
kdf_obj = OBJ_txt2obj(ropt->kdf, 0);
|
||||
if (kdf_obj == NULL) {
|
||||
BIO_printf(bio_err, "Unknown KDF %s\n", ropt->kdf);
|
||||
goto end;
|
||||
}
|
||||
/* Only works for OIDs without params */
|
||||
if (!X509_ALGOR_set0(kdf_algo, kdf_obj, V_ASN1_UNDEF, NULL))
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (secret_key != NULL) {
|
||||
if (!CMS_add0_recipient_key(cms, NID_undef,
|
||||
secret_key, secret_keylen,
|
||||
|
@ -1315,6 +1419,14 @@ int cms_main(int argc, char **argv)
|
|||
OPENSSL_free(key_param);
|
||||
key_param = tparam;
|
||||
}
|
||||
for (recip_opt = recip_first; recip_opt != NULL;) {
|
||||
cms_recip_opt *topt;
|
||||
|
||||
OPENSSL_free(recip_opt->ukm_data);
|
||||
topt = recip_opt->next;
|
||||
OPENSSL_free(recip_opt);
|
||||
recip_opt = topt;
|
||||
}
|
||||
X509_STORE_free(store);
|
||||
X509_free(cert);
|
||||
X509_free(recip);
|
||||
|
|
|
@ -3047,15 +3047,11 @@ BIO *dup_bio_out(int format)
|
|||
{
|
||||
BIO *b = BIO_new_fp(stdout,
|
||||
BIO_NOCLOSE | (FMT_istext(format) ? BIO_FP_TEXT : 0));
|
||||
void *prefix = NULL;
|
||||
BIO *btmp;
|
||||
|
||||
if (b == NULL)
|
||||
return NULL;
|
||||
|
||||
#ifdef OPENSSL_SYS_VMS
|
||||
if (FMT_istext(format)) {
|
||||
btmp = BIO_new(BIO_f_linebuffer());
|
||||
if (b != NULL && FMT_istext(format)) {
|
||||
BIO *btmp = BIO_new(BIO_f_linebuffer());
|
||||
|
||||
if (btmp == NULL) {
|
||||
BIO_free(b);
|
||||
return NULL;
|
||||
|
@ -3064,17 +3060,6 @@ BIO *dup_bio_out(int format)
|
|||
}
|
||||
#endif
|
||||
|
||||
if (FMT_istext(format)
|
||||
&& (prefix = getenv("HARNESS_OSSL_PREFIX")) != NULL) {
|
||||
btmp = BIO_new(BIO_f_prefix());
|
||||
if (btmp == NULL) {
|
||||
BIO_free_all(b);
|
||||
return NULL;
|
||||
}
|
||||
b = BIO_push(btmp, b);
|
||||
BIO_set_prefix(b, prefix);
|
||||
}
|
||||
|
||||
return b;
|
||||
}
|
||||
|
||||
|
|
|
@ -635,7 +635,7 @@ static int bring_ocsp_resp_in_correct_order(SSL *s, tlsextstatusctx *srctx,
|
|||
/* reserve enough space so the pushes to the stack would not fail */
|
||||
*sk_resp = sk_OCSP_RESPONSE_new_reserve(NULL, num);
|
||||
|
||||
if (sk_resp == NULL)
|
||||
if (*sk_resp == NULL)
|
||||
return SSL_TLSEXT_ERR_ALERT_FATAL;
|
||||
|
||||
for (i = 0; i < num; i++) {
|
||||
|
@ -755,8 +755,10 @@ static int get_ocsp_resp_from_responder(SSL *s, tlsextstatusctx *srctx,
|
|||
STACK_OF(X509) *server_certs = NULL;
|
||||
OCSP_RESPONSE *resp = NULL;
|
||||
|
||||
if (*sk_resp != NULL)
|
||||
if (*sk_resp != NULL) {
|
||||
sk_OCSP_RESPONSE_pop_free(*sk_resp, OCSP_RESPONSE_free);
|
||||
*sk_resp = NULL;
|
||||
}
|
||||
|
||||
SSL_get0_chain_certs(s, &server_certs);
|
||||
/*
|
||||
|
@ -784,7 +786,7 @@ static int get_ocsp_resp_from_responder(SSL *s, tlsextstatusctx *srctx,
|
|||
|
||||
*sk_resp = sk_OCSP_RESPONSE_new_reserve(NULL, num);
|
||||
|
||||
if (sk_resp == NULL)
|
||||
if (*sk_resp == NULL)
|
||||
return SSL_TLSEXT_ERR_ALERT_FATAL;
|
||||
|
||||
/* for each certificate in chain (except root) get the OCSP response */
|
||||
|
|
|
@ -97,10 +97,10 @@ SOURCE[../providers/libfips.a]=$CORE_COMMON
|
|||
# Central utilities
|
||||
$UTIL_COMMON=\
|
||||
cryptlib.c params.c params_from_text.c bsearch.c ex_data.c o_str.c \
|
||||
threads_pthread.c threads_win.c threads_none.c threads_common.c \
|
||||
initthread.c context.c sparse_array.c asn1_dsa.c packet.c \
|
||||
param_build.c param_build_set.c der_writer.c threads_lib.c \
|
||||
params_dup.c time.c
|
||||
threads_lock_contention.c threads_pthread.c threads_win.c \
|
||||
threads_none.c threads_common.c initthread.c context.c sparse_array.c \
|
||||
asn1_dsa.c packet.c param_build.c param_build_set.c der_writer.c \
|
||||
threads_lib.c params_dup.c time.c
|
||||
|
||||
SOURCE[../libcrypto]=$UTIL_COMMON \
|
||||
mem.c mem_sec.c \
|
||||
|
|
|
@ -2,4 +2,4 @@ LIBS=../../libcrypto
|
|||
SOURCE[../../libcrypto]= \
|
||||
cms_lib.c cms_asn1.c cms_att.c cms_io.c cms_smime.c cms_err.c \
|
||||
cms_sd.c cms_dd.c cms_cd.c cms_env.c cms_enc.c cms_ess.c \
|
||||
cms_pwri.c cms_kari.c cms_rsa.c cms_dh.c cms_ec.c
|
||||
cms_pwri.c cms_kari.c cms_rsa.c cms_dh.c cms_ec.c cms_kem.c cms_kemri.c
|
||||
|
|
|
@ -201,10 +201,52 @@ ASN1_SEQUENCE(CMS_PasswordRecipientInfo) = {
|
|||
ASN1_SIMPLE(CMS_PasswordRecipientInfo, encryptedKey, ASN1_OCTET_STRING)
|
||||
} ASN1_SEQUENCE_END(CMS_PasswordRecipientInfo)
|
||||
|
||||
static int cms_kemri_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
|
||||
void *exarg)
|
||||
{
|
||||
CMS_KEMRecipientInfo *kemri = (CMS_KEMRecipientInfo *)*pval;
|
||||
|
||||
if (operation == ASN1_OP_NEW_POST) {
|
||||
kemri->ctx = EVP_CIPHER_CTX_new();
|
||||
if (kemri->ctx == NULL)
|
||||
return 0;
|
||||
EVP_CIPHER_CTX_set_flags(kemri->ctx, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW);
|
||||
kemri->pctx = NULL;
|
||||
} else if (operation == ASN1_OP_FREE_POST) {
|
||||
EVP_PKEY_CTX_free(kemri->pctx);
|
||||
EVP_CIPHER_CTX_free(kemri->ctx);
|
||||
ASN1_OCTET_STRING_free(kemri->ukm);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
ASN1_SEQUENCE_cb(CMS_KEMRecipientInfo, cms_kemri_cb) = {
|
||||
ASN1_EMBED(CMS_KEMRecipientInfo, version, INT32),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, rid, CMS_SignerIdentifier),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, kem, X509_ALGOR),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, kemct, ASN1_OCTET_STRING),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, kdf, X509_ALGOR),
|
||||
ASN1_EMBED(CMS_KEMRecipientInfo, kekLength, INT32),
|
||||
ASN1_EXP_OPT(CMS_KEMRecipientInfo, ukm, ASN1_OCTET_STRING, 0),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, wrap, X509_ALGOR),
|
||||
ASN1_SIMPLE(CMS_KEMRecipientInfo, encryptedKey, ASN1_OCTET_STRING)
|
||||
} ASN1_SEQUENCE_END_cb(CMS_KEMRecipientInfo, CMS_KEMRecipientInfo)
|
||||
|
||||
ASN1_ADB_TEMPLATE(ori_def) = ASN1_SIMPLE(CMS_OtherRecipientInfo, d.other, ASN1_ANY);
|
||||
|
||||
ASN1_ADB(CMS_OtherRecipientInfo) = {
|
||||
ADB_ENTRY(NID_id_smime_ori_kem, ASN1_SIMPLE(CMS_OtherRecipientInfo, d.kemri,
|
||||
CMS_KEMRecipientInfo))
|
||||
} ASN1_ADB_END(CMS_OtherRecipientInfo, 0, oriType, 0, &ori_def_tt, NULL);
|
||||
|
||||
DECLARE_ASN1_FUNCTIONS(CMS_OtherRecipientInfo)
|
||||
|
||||
ASN1_SEQUENCE(CMS_OtherRecipientInfo) = {
|
||||
ASN1_SIMPLE(CMS_OtherRecipientInfo, oriType, ASN1_OBJECT),
|
||||
ASN1_OPT(CMS_OtherRecipientInfo, oriValue, ASN1_ANY)
|
||||
} static_ASN1_SEQUENCE_END(CMS_OtherRecipientInfo)
|
||||
ASN1_ADB_OBJECT(CMS_OtherRecipientInfo)
|
||||
} ASN1_SEQUENCE_END(CMS_OtherRecipientInfo)
|
||||
|
||||
IMPLEMENT_ASN1_FUNCTIONS(CMS_OtherRecipientInfo)
|
||||
|
||||
/* Free up RecipientInfo additional data */
|
||||
static int cms_ri_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
|
||||
|
@ -224,6 +266,23 @@ static int cms_ri_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
|
|||
CMS_PasswordRecipientInfo *pwri = ri->d.pwri;
|
||||
OPENSSL_clear_free(pwri->pass, pwri->passlen);
|
||||
}
|
||||
} else if (operation == ASN1_OP_D2I_POST) {
|
||||
CMS_RecipientInfo *ri = (CMS_RecipientInfo *)*pval;
|
||||
|
||||
ri->type = ri->encoded_type;
|
||||
if (ri->type == CMS_RECIPINFO_OTHER) {
|
||||
int nid;
|
||||
|
||||
nid = OBJ_obj2nid(ri->d.ori->oriType);
|
||||
/* For ORI, map NID to specific type */
|
||||
if (nid == NID_id_smime_ori_kem)
|
||||
ri->type = CMS_RECIPINFO_KEM;
|
||||
/* Otherwise stay with generic CMS_RECIPINFO_OTHER type */
|
||||
}
|
||||
} else if (operation == ASN1_OP_NEW_POST) {
|
||||
CMS_RecipientInfo *ri = (CMS_RecipientInfo *)*pval;
|
||||
|
||||
ri->type = ri->encoded_type;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
@ -234,7 +293,7 @@ ASN1_CHOICE_cb(CMS_RecipientInfo, cms_ri_cb) = {
|
|||
ASN1_IMP(CMS_RecipientInfo, d.kekri, CMS_KEKRecipientInfo, 2),
|
||||
ASN1_IMP(CMS_RecipientInfo, d.pwri, CMS_PasswordRecipientInfo, 3),
|
||||
ASN1_IMP(CMS_RecipientInfo, d.ori, CMS_OtherRecipientInfo, 4)
|
||||
} ASN1_CHOICE_END_cb(CMS_RecipientInfo, CMS_RecipientInfo, type)
|
||||
} ASN1_CHOICE_END_cb(CMS_RecipientInfo, CMS_RecipientInfo, encoded_type)
|
||||
|
||||
ASN1_NDEF_SEQUENCE(CMS_EnvelopedData) = {
|
||||
ASN1_EMBED(CMS_EnvelopedData, version, INT32),
|
||||
|
@ -430,3 +489,33 @@ int CMS_SharedInfo_encode(unsigned char **pder, X509_ALGOR *kekalg,
|
|||
intsi.pecsi = &ecsi;
|
||||
return ASN1_item_i2d(intsi.a, pder, ASN1_ITEM_rptr(CMS_SharedInfo));
|
||||
}
|
||||
|
||||
/*
|
||||
* Utilities to encode the CMS_CMSORIforKEMOtherInfo structure used during key
|
||||
* derivation.
|
||||
*/
|
||||
|
||||
typedef struct {
|
||||
X509_ALGOR *wrap;
|
||||
uint32_t kekLength;
|
||||
ASN1_OCTET_STRING *ukm;
|
||||
} CMS_CMSORIforKEMOtherInfo;
|
||||
|
||||
ASN1_SEQUENCE(CMS_CMSORIforKEMOtherInfo) = {
|
||||
ASN1_SIMPLE(CMS_CMSORIforKEMOtherInfo, wrap, X509_ALGOR),
|
||||
ASN1_EMBED(CMS_CMSORIforKEMOtherInfo, kekLength, INT32),
|
||||
ASN1_EXP_OPT(CMS_CMSORIforKEMOtherInfo, ukm, ASN1_OCTET_STRING, 0),
|
||||
} static_ASN1_SEQUENCE_END(CMS_CMSORIforKEMOtherInfo)
|
||||
|
||||
int CMS_CMSORIforKEMOtherInfo_encode(unsigned char **pder, X509_ALGOR *wrap,
|
||||
ASN1_OCTET_STRING *ukm, int keylen)
|
||||
{
|
||||
CMS_CMSORIforKEMOtherInfo kem_otherinfo;
|
||||
|
||||
kem_otherinfo.wrap = wrap;
|
||||
kem_otherinfo.kekLength = keylen;
|
||||
kem_otherinfo.ukm = ukm;
|
||||
|
||||
return ASN1_item_i2d((ASN1_VALUE *)&kem_otherinfo, pder,
|
||||
ASN1_ITEM_rptr(CMS_CMSORIforKEMOtherInfo));
|
||||
}
|
||||
|
|
|
@ -7,6 +7,12 @@
|
|||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Low level key APIs (DH etc) are deprecated for public use, but still ok for
|
||||
* internal use.
|
||||
*/
|
||||
#include "internal/deprecated.h"
|
||||
|
||||
#include "internal/cryptlib.h"
|
||||
#include <openssl/asn1t.h>
|
||||
#include <openssl/pem.h>
|
||||
|
@ -14,6 +20,7 @@
|
|||
#include <openssl/err.h>
|
||||
#include <openssl/cms.h>
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/core_names.h>
|
||||
#include "internal/sizes.h"
|
||||
#include "crypto/asn1.h"
|
||||
#include "crypto/evp.h"
|
||||
|
@ -111,9 +118,12 @@ int ossl_cms_env_asn1_ctrl(CMS_RecipientInfo *ri, int cmd)
|
|||
{
|
||||
EVP_PKEY *pkey;
|
||||
int i;
|
||||
if (ri->type == CMS_RECIPINFO_TRANS)
|
||||
|
||||
switch (ri->type) {
|
||||
case CMS_RECIPINFO_TRANS:
|
||||
pkey = ri->d.ktri->pkey;
|
||||
else if (ri->type == CMS_RECIPINFO_AGREE) {
|
||||
break;
|
||||
case CMS_RECIPINFO_AGREE: {
|
||||
EVP_PKEY_CTX *pctx = ri->d.kari->pctx;
|
||||
|
||||
if (pctx == NULL)
|
||||
|
@ -121,8 +131,13 @@ int ossl_cms_env_asn1_ctrl(CMS_RecipientInfo *ri, int cmd)
|
|||
pkey = EVP_PKEY_CTX_get0_pkey(pctx);
|
||||
if (pkey == NULL)
|
||||
return 0;
|
||||
} else
|
||||
break;
|
||||
}
|
||||
case CMS_RECIPINFO_KEM:
|
||||
return ossl_cms_kem_envelope(ri, cmd);
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (EVP_PKEY_is_a(pkey, "DHX") || EVP_PKEY_is_a(pkey, "DH"))
|
||||
return ossl_cms_dh_envelope(ri, cmd);
|
||||
|
@ -202,6 +217,9 @@ void ossl_cms_RecipientInfos_set_cmsctx(CMS_ContentInfo *cms)
|
|||
case CMS_RECIPINFO_PASS:
|
||||
ri->d.pwri->cms_ctx = ctx;
|
||||
break;
|
||||
case CMS_RECIPINFO_KEM:
|
||||
ri->d.ori->d.kemri->cms_ctx = ctx;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -220,6 +238,8 @@ EVP_PKEY_CTX *CMS_RecipientInfo_get0_pkey_ctx(CMS_RecipientInfo *ri)
|
|||
return ri->d.ktri->pctx;
|
||||
else if (ri->type == CMS_RECIPINFO_AGREE)
|
||||
return ri->d.kari->pctx;
|
||||
else if (ri->type == CMS_RECIPINFO_KEM)
|
||||
return ri->d.ori->d.kemri->pctx;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -336,7 +356,7 @@ static int cms_RecipientInfo_ktri_init(CMS_RecipientInfo *ri, X509 *recip,
|
|||
ri->d.ktri = M_ASN1_new_of(CMS_KeyTransRecipientInfo);
|
||||
if (!ri->d.ktri)
|
||||
return 0;
|
||||
ri->type = CMS_RECIPINFO_TRANS;
|
||||
ri->encoded_type = ri->type = CMS_RECIPINFO_TRANS;
|
||||
|
||||
ktri = ri->d.ktri;
|
||||
ktri->cms_ctx = ctx;
|
||||
|
@ -423,6 +443,11 @@ CMS_RecipientInfo *CMS_add1_recipient(CMS_ContentInfo *cms, X509 *recip,
|
|||
goto err;
|
||||
break;
|
||||
|
||||
case CMS_RECIPINFO_KEM:
|
||||
if (!ossl_cms_RecipientInfo_kemri_init(ri, recip, pk, flags, ctx))
|
||||
goto err;
|
||||
break;
|
||||
|
||||
default:
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
|
||||
goto err;
|
||||
|
@ -750,7 +775,7 @@ CMS_RecipientInfo *CMS_add0_recipient_key(CMS_ContentInfo *cms, int nid,
|
|||
ERR_raise(ERR_LIB_CMS, ERR_R_ASN1_LIB);
|
||||
goto err;
|
||||
}
|
||||
ri->type = CMS_RECIPINFO_KEK;
|
||||
ri->encoded_type = ri->type = CMS_RECIPINFO_KEK;
|
||||
|
||||
kekri = ri->d.kekri;
|
||||
|
||||
|
@ -1025,6 +1050,9 @@ int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
|
|||
case CMS_RECIPINFO_PASS:
|
||||
return ossl_cms_RecipientInfo_pwri_crypt(cms, ri, 0);
|
||||
|
||||
case CMS_RECIPINFO_KEM:
|
||||
return ossl_cms_RecipientInfo_kemri_decrypt(cms, ri);
|
||||
|
||||
default:
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_RECIPIENTINFO_TYPE);
|
||||
return 0;
|
||||
|
@ -1046,6 +1074,9 @@ int CMS_RecipientInfo_encrypt(const CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
|
|||
case CMS_RECIPINFO_PASS:
|
||||
return ossl_cms_RecipientInfo_pwri_crypt(cms, ri, 1);
|
||||
|
||||
case CMS_RECIPINFO_KEM:
|
||||
return ossl_cms_RecipientInfo_kemri_encrypt(cms, ri);
|
||||
|
||||
default:
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_RECIPIENT_TYPE);
|
||||
return 0;
|
||||
|
@ -1100,7 +1131,8 @@ static void cms_env_set_version(CMS_EnvelopedData *env)
|
|||
|
||||
for (i = 0; i < sk_CMS_RecipientInfo_num(env->recipientInfos); i++) {
|
||||
ri = sk_CMS_RecipientInfo_value(env->recipientInfos, i);
|
||||
if (ri->type == CMS_RECIPINFO_PASS || ri->type == CMS_RECIPINFO_OTHER) {
|
||||
if (ri->type == CMS_RECIPINFO_PASS || ri->type == CMS_RECIPINFO_OTHER
|
||||
|| ri->type == CMS_RECIPINFO_KEM) {
|
||||
env->version = 3;
|
||||
return;
|
||||
} else if (ri->type != CMS_RECIPINFO_TRANS
|
||||
|
@ -1337,6 +1369,18 @@ err:
|
|||
*/
|
||||
int ossl_cms_pkey_get_ri_type(EVP_PKEY *pk)
|
||||
{
|
||||
int ri_type;
|
||||
EVP_PKEY_CTX *ctx = NULL;
|
||||
|
||||
/*
|
||||
* First check the provider for RecipientInfo support since a key may support
|
||||
* multiple types, e.g. an RSA key and provider may support RSA key transport
|
||||
* and/or RSA-KEM.
|
||||
*/
|
||||
if (evp_pkey_is_provided(pk)
|
||||
&& EVP_PKEY_get_int_param(pk, OSSL_PKEY_PARAM_CMS_RI_TYPE, &ri_type))
|
||||
return ri_type;
|
||||
|
||||
/* Check types that we know about */
|
||||
if (EVP_PKEY_is_a(pk, "DH"))
|
||||
return CMS_RECIPINFO_AGREE;
|
||||
|
@ -1350,7 +1394,7 @@ int ossl_cms_pkey_get_ri_type(EVP_PKEY *pk)
|
|||
return CMS_RECIPINFO_TRANS;
|
||||
|
||||
/*
|
||||
* Otherwise this might ben an engine implementation, so see if we can get
|
||||
* Otherwise this might be an engine implementation, so see if we can get
|
||||
* the type from the ameth.
|
||||
*/
|
||||
if (pk->ameth && pk->ameth->pkey_ctrl) {
|
||||
|
@ -1359,7 +1403,25 @@ int ossl_cms_pkey_get_ri_type(EVP_PKEY *pk)
|
|||
if (i > 0)
|
||||
return r;
|
||||
}
|
||||
return CMS_RECIPINFO_TRANS;
|
||||
|
||||
/*
|
||||
* Otherwise try very hard to figure out what RecipientInfo the key supports.
|
||||
*/
|
||||
ri_type = CMS_RECIPINFO_TRANS;
|
||||
ctx = EVP_PKEY_CTX_new(pk, NULL);
|
||||
if (ctx != NULL) {
|
||||
ERR_set_mark();
|
||||
if (EVP_PKEY_encrypt_init(ctx) > 0)
|
||||
ri_type = CMS_RECIPINFO_TRANS;
|
||||
else if (EVP_PKEY_derive_init(ctx) > 0)
|
||||
ri_type = CMS_RECIPINFO_AGREE;
|
||||
else if (EVP_PKEY_encapsulate_init(ctx, NULL) > 0)
|
||||
ri_type = CMS_RECIPINFO_KEM;
|
||||
ERR_pop_to_mark();
|
||||
}
|
||||
EVP_PKEY_CTX_free(ctx);
|
||||
|
||||
return ri_type;
|
||||
}
|
||||
|
||||
int ossl_cms_pkey_is_ri_type_supported(EVP_PKEY *pk, int ri_type)
|
||||
|
@ -1381,3 +1443,79 @@ int ossl_cms_pkey_is_ri_type_supported(EVP_PKEY *pk, int ri_type)
|
|||
|
||||
return (supportedRiType == ri_type);
|
||||
}
|
||||
|
||||
int ossl_cms_RecipientInfo_wrap_init(CMS_RecipientInfo *ri,
|
||||
const EVP_CIPHER *cipher)
|
||||
{
|
||||
const CMS_CTX *cms_ctx;
|
||||
EVP_CIPHER_CTX *ctx;
|
||||
const EVP_CIPHER *kekcipher;
|
||||
EVP_CIPHER *fetched_kekcipher;
|
||||
const char *kekcipher_name;
|
||||
int keylen;
|
||||
int ret;
|
||||
|
||||
if (ri->type == CMS_RECIPINFO_AGREE) {
|
||||
cms_ctx = ri->d.kari->cms_ctx;
|
||||
ctx = ri->d.kari->ctx;
|
||||
} else if (ri->type == CMS_RECIPINFO_KEM) {
|
||||
cms_ctx = ri->d.ori->d.kemri->cms_ctx;
|
||||
ctx = ri->d.ori->d.kemri->ctx;
|
||||
} else {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_RECIPIENTINFO_TYPE);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* If a suitable wrap algorithm is already set nothing to do */
|
||||
kekcipher = EVP_CIPHER_CTX_get0_cipher(ctx);
|
||||
if (kekcipher != NULL) {
|
||||
if (EVP_CIPHER_CTX_get_mode(ctx) != EVP_CIPH_WRAP_MODE)
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
if (cipher == NULL)
|
||||
return 0;
|
||||
keylen = EVP_CIPHER_get_key_length(cipher);
|
||||
if (keylen <= 0) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_INVALID_KEY_LENGTH);
|
||||
return 0;
|
||||
}
|
||||
if ((EVP_CIPHER_get_flags(cipher) & EVP_CIPH_FLAG_GET_WRAP_CIPHER) != 0) {
|
||||
ret = EVP_CIPHER_meth_get_ctrl(cipher)(NULL, EVP_CTRL_GET_WRAP_CIPHER,
|
||||
0, &kekcipher);
|
||||
if (ret <= 0)
|
||||
return 0;
|
||||
|
||||
if (kekcipher != NULL) {
|
||||
if (EVP_CIPHER_get_mode(kekcipher) != EVP_CIPH_WRAP_MODE)
|
||||
return 0;
|
||||
kekcipher_name = EVP_CIPHER_get0_name(kekcipher);
|
||||
goto enc;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Pick a cipher based on content encryption cipher. If it is DES3 use
|
||||
* DES3 wrap otherwise use AES wrap similar to key size.
|
||||
*/
|
||||
#ifndef OPENSSL_NO_DES
|
||||
if (EVP_CIPHER_get_type(cipher) == NID_des_ede3_cbc)
|
||||
kekcipher_name = SN_id_smime_alg_CMS3DESwrap;
|
||||
else
|
||||
#endif
|
||||
if (keylen <= 16)
|
||||
kekcipher_name = SN_id_aes128_wrap;
|
||||
else if (keylen <= 24)
|
||||
kekcipher_name = SN_id_aes192_wrap;
|
||||
else
|
||||
kekcipher_name = SN_id_aes256_wrap;
|
||||
enc:
|
||||
fetched_kekcipher = EVP_CIPHER_fetch(ossl_cms_ctx_get0_libctx(cms_ctx),
|
||||
kekcipher_name,
|
||||
ossl_cms_ctx_get0_propq(cms_ctx));
|
||||
if (fetched_kekcipher == NULL)
|
||||
return 0;
|
||||
ret = EVP_EncryptInit_ex(ctx, fetched_kekcipher, NULL, NULL, NULL);
|
||||
EVP_CIPHER_free(fetched_kekcipher);
|
||||
return ret;
|
||||
}
|
||||
|
|
|
@ -88,6 +88,7 @@ static const ERR_STRING_DATA CMS_str_reasons[] = {
|
|||
"not a signed receipt"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_ENCRYPTED_DATA), "not encrypted data"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEK), "not kek"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEM), "not kem"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEY_AGREEMENT), "not key agreement"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEY_TRANSPORT), "not key transport"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_PWRI), "not pwri"},
|
||||
|
@ -140,6 +141,8 @@ static const ERR_STRING_DATA CMS_str_reasons[] = {
|
|||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_DIGEST_ALGORITHM),
|
||||
"unknown digest algorithm"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_ID), "unknown id"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_KDF_ALGORITHM),
|
||||
"unknown kdf algorithm"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM),
|
||||
"unsupported compression algorithm"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_CONTENT_ENCRYPTION_ALGORITHM),
|
||||
|
@ -148,6 +151,8 @@ static const ERR_STRING_DATA CMS_str_reasons[] = {
|
|||
"unsupported content type"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_ENCRYPTION_TYPE),
|
||||
"unsupported encryption type"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_KDF_ALGORITHM),
|
||||
"unsupported kdf algorithm"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_KEK_ALGORITHM),
|
||||
"unsupported kek algorithm"},
|
||||
{ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM),
|
||||
|
|
|
@ -7,12 +7,6 @@
|
|||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Low level key APIs (DH etc) are deprecated for public use, but still ok for
|
||||
* internal use.
|
||||
*/
|
||||
#include "internal/deprecated.h"
|
||||
|
||||
#include "internal/cryptlib.h"
|
||||
#include <openssl/asn1t.h>
|
||||
#include <openssl/pem.h>
|
||||
|
@ -349,7 +343,7 @@ int ossl_cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
|
|||
ri->d.kari = M_ASN1_new_of(CMS_KeyAgreeRecipientInfo);
|
||||
if (ri->d.kari == NULL)
|
||||
return 0;
|
||||
ri->type = CMS_RECIPINFO_AGREE;
|
||||
ri->encoded_type = ri->type = CMS_RECIPINFO_AGREE;
|
||||
|
||||
kari = ri->d.kari;
|
||||
kari->version = 3;
|
||||
|
@ -412,67 +406,6 @@ int ossl_cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
|
|||
return 1;
|
||||
}
|
||||
|
||||
static int cms_wrap_init(CMS_KeyAgreeRecipientInfo *kari,
|
||||
const EVP_CIPHER *cipher)
|
||||
{
|
||||
const CMS_CTX *cms_ctx = kari->cms_ctx;
|
||||
EVP_CIPHER_CTX *ctx = kari->ctx;
|
||||
const EVP_CIPHER *kekcipher;
|
||||
EVP_CIPHER *fetched_kekcipher;
|
||||
const char *kekcipher_name;
|
||||
int keylen;
|
||||
int ret;
|
||||
|
||||
/* If a suitable wrap algorithm is already set nothing to do */
|
||||
kekcipher = EVP_CIPHER_CTX_get0_cipher(ctx);
|
||||
if (kekcipher != NULL) {
|
||||
if (EVP_CIPHER_CTX_get_mode(ctx) != EVP_CIPH_WRAP_MODE)
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
if (cipher == NULL)
|
||||
return 0;
|
||||
keylen = EVP_CIPHER_get_key_length(cipher);
|
||||
if ((EVP_CIPHER_get_flags(cipher) & EVP_CIPH_FLAG_GET_WRAP_CIPHER) != 0) {
|
||||
ret = EVP_CIPHER_meth_get_ctrl(cipher)(NULL, EVP_CTRL_GET_WRAP_CIPHER,
|
||||
0, &kekcipher);
|
||||
if (ret <= 0)
|
||||
return 0;
|
||||
|
||||
if (kekcipher != NULL) {
|
||||
if (EVP_CIPHER_get_mode(kekcipher) != EVP_CIPH_WRAP_MODE)
|
||||
return 0;
|
||||
kekcipher_name = EVP_CIPHER_get0_name(kekcipher);
|
||||
goto enc;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Pick a cipher based on content encryption cipher. If it is DES3 use
|
||||
* DES3 wrap otherwise use AES wrap similar to key size.
|
||||
*/
|
||||
#ifndef OPENSSL_NO_DES
|
||||
if (EVP_CIPHER_get_type(cipher) == NID_des_ede3_cbc)
|
||||
kekcipher_name = SN_id_smime_alg_CMS3DESwrap;
|
||||
else
|
||||
#endif
|
||||
if (keylen <= 16)
|
||||
kekcipher_name = SN_id_aes128_wrap;
|
||||
else if (keylen <= 24)
|
||||
kekcipher_name = SN_id_aes192_wrap;
|
||||
else
|
||||
kekcipher_name = SN_id_aes256_wrap;
|
||||
enc:
|
||||
fetched_kekcipher = EVP_CIPHER_fetch(ossl_cms_ctx_get0_libctx(cms_ctx),
|
||||
kekcipher_name,
|
||||
ossl_cms_ctx_get0_propq(cms_ctx));
|
||||
if (fetched_kekcipher == NULL)
|
||||
return 0;
|
||||
ret = EVP_EncryptInit_ex(ctx, fetched_kekcipher, NULL, NULL, NULL);
|
||||
EVP_CIPHER_free(fetched_kekcipher);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Encrypt content key in key agreement recipient info */
|
||||
|
||||
int ossl_cms_RecipientInfo_kari_encrypt(const CMS_ContentInfo *cms,
|
||||
|
@ -492,7 +425,7 @@ int ossl_cms_RecipientInfo_kari_encrypt(const CMS_ContentInfo *cms,
|
|||
reks = kari->recipientEncryptedKeys;
|
||||
ec = ossl_cms_get0_env_enc_content(cms);
|
||||
/* Initialise wrap algorithm parameters */
|
||||
if (!cms_wrap_init(kari, ec->cipher))
|
||||
if (!ossl_cms_RecipientInfo_wrap_init(ri, ec->cipher))
|
||||
return 0;
|
||||
/*
|
||||
* If no originator key set up initialise for ephemeral key the public key
|
||||
|
|
|
@ -0,0 +1,163 @@
|
|||
/*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <limits.h>
|
||||
#include <openssl/cms.h>
|
||||
#include <openssl/core_names.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/decoder.h>
|
||||
#include "internal/sizes.h"
|
||||
#include "crypto/asn1.h"
|
||||
#include "crypto/evp.h"
|
||||
#include "cms_local.h"
|
||||
|
||||
static int kem_cms_decrypt(CMS_RecipientInfo *ri)
|
||||
{
|
||||
uint32_t *kekLength;
|
||||
X509_ALGOR *wrap;
|
||||
EVP_PKEY_CTX *pctx;
|
||||
EVP_CIPHER_CTX *kekctx;
|
||||
uint32_t cipher_length;
|
||||
char name[OSSL_MAX_NAME_SIZE];
|
||||
EVP_CIPHER *kekcipher = NULL;
|
||||
int rv = 0;
|
||||
|
||||
if (!ossl_cms_RecipientInfo_kemri_get0_alg(ri, &kekLength, &wrap))
|
||||
goto err;
|
||||
|
||||
pctx = CMS_RecipientInfo_get0_pkey_ctx(ri);
|
||||
if (pctx == NULL)
|
||||
goto err;
|
||||
|
||||
kekctx = CMS_RecipientInfo_kemri_get0_ctx(ri);
|
||||
if (kekctx == NULL)
|
||||
goto err;
|
||||
|
||||
OBJ_obj2txt(name, sizeof(name), wrap->algorithm, 0);
|
||||
kekcipher = EVP_CIPHER_fetch(pctx->libctx, name, pctx->propquery);
|
||||
if (kekcipher == NULL || EVP_CIPHER_get_mode(kekcipher) != EVP_CIPH_WRAP_MODE)
|
||||
goto err;
|
||||
if (!EVP_EncryptInit_ex(kekctx, kekcipher, NULL, NULL, NULL))
|
||||
goto err;
|
||||
if (EVP_CIPHER_asn1_to_param(kekctx, wrap->parameter) <= 0)
|
||||
goto err;
|
||||
|
||||
cipher_length = EVP_CIPHER_CTX_get_key_length(kekctx);
|
||||
if (cipher_length != *kekLength) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_INVALID_KEY_LENGTH);
|
||||
goto err;
|
||||
}
|
||||
|
||||
rv = 1;
|
||||
err:
|
||||
EVP_CIPHER_free(kekcipher);
|
||||
return rv;
|
||||
}
|
||||
|
||||
static int kem_cms_encrypt(CMS_RecipientInfo *ri)
|
||||
{
|
||||
uint32_t *kekLength;
|
||||
X509_ALGOR *wrap;
|
||||
X509_ALGOR *kdf;
|
||||
EVP_PKEY_CTX *pctx;
|
||||
EVP_PKEY *pkey;
|
||||
int security_bits;
|
||||
const ASN1_OBJECT *kdf_obj = NULL;
|
||||
unsigned char kemri_x509_algor[OSSL_MAX_ALGORITHM_ID_SIZE];
|
||||
OSSL_PARAM params[2];
|
||||
X509_ALGOR *x509_algor = NULL;
|
||||
EVP_CIPHER_CTX *kekctx;
|
||||
int wrap_nid;
|
||||
int rv = 0;
|
||||
|
||||
if (!ossl_cms_RecipientInfo_kemri_get0_alg(ri, &kekLength, &wrap))
|
||||
goto err;
|
||||
|
||||
kdf = CMS_RecipientInfo_kemri_get0_kdf_alg(ri);
|
||||
if (kdf == NULL)
|
||||
goto err;
|
||||
|
||||
pctx = CMS_RecipientInfo_get0_pkey_ctx(ri);
|
||||
if (pctx == NULL)
|
||||
goto err;
|
||||
|
||||
pkey = EVP_PKEY_CTX_get0_pkey(pctx);
|
||||
if (pkey == NULL)
|
||||
goto err;
|
||||
|
||||
security_bits = EVP_PKEY_get_security_bits(pkey);
|
||||
if (security_bits == 0)
|
||||
goto err;
|
||||
|
||||
X509_ALGOR_get0(&kdf_obj, NULL, NULL, kdf);
|
||||
if (kdf_obj == NULL || OBJ_obj2nid(kdf_obj) == NID_undef) {
|
||||
/*
|
||||
* If the KDF OID hasn't already been set, then query the provider
|
||||
* for a default KDF.
|
||||
*/
|
||||
params[0] = OSSL_PARAM_construct_octet_string(OSSL_PKEY_PARAM_CMS_KEMRI_KDF_ALGORITHM,
|
||||
kemri_x509_algor, sizeof(kemri_x509_algor));
|
||||
params[1] = OSSL_PARAM_construct_end();
|
||||
if (!EVP_PKEY_get_params(pkey, params))
|
||||
goto err;
|
||||
if (OSSL_PARAM_modified(¶ms[0])) {
|
||||
const unsigned char *p = kemri_x509_algor;
|
||||
|
||||
x509_algor = d2i_X509_ALGOR(NULL, &p, (long)params[0].return_size);
|
||||
if (x509_algor == NULL)
|
||||
goto err;
|
||||
if (!X509_ALGOR_copy(kdf, x509_algor))
|
||||
goto err;
|
||||
} else {
|
||||
if (!X509_ALGOR_set0(kdf, OBJ_nid2obj(NID_HKDF_SHA256), V_ASN1_UNDEF, NULL))
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* Get wrap NID */
|
||||
kekctx = CMS_RecipientInfo_kemri_get0_ctx(ri);
|
||||
if (kekctx == NULL)
|
||||
goto err;
|
||||
*kekLength = EVP_CIPHER_CTX_get_key_length(kekctx);
|
||||
wrap_nid = EVP_CIPHER_CTX_get_type(kekctx);
|
||||
|
||||
/* Package wrap algorithm in an AlgorithmIdentifier */
|
||||
ASN1_OBJECT_free(wrap->algorithm);
|
||||
ASN1_TYPE_free(wrap->parameter);
|
||||
wrap->algorithm = OBJ_nid2obj(wrap_nid);
|
||||
wrap->parameter = ASN1_TYPE_new();
|
||||
if (wrap->parameter == NULL)
|
||||
goto err;
|
||||
if (EVP_CIPHER_param_to_asn1(kekctx, wrap->parameter) <= 0)
|
||||
goto err;
|
||||
if (ASN1_TYPE_get(wrap->parameter) == NID_undef) {
|
||||
ASN1_TYPE_free(wrap->parameter);
|
||||
wrap->parameter = NULL;
|
||||
}
|
||||
|
||||
rv = 1;
|
||||
err:
|
||||
X509_ALGOR_free(x509_algor);
|
||||
return rv;
|
||||
}
|
||||
|
||||
int ossl_cms_kem_envelope(CMS_RecipientInfo *ri, int decrypt)
|
||||
{
|
||||
assert(decrypt == 0 || decrypt == 1);
|
||||
|
||||
if (decrypt == 1)
|
||||
return kem_cms_decrypt(ri);
|
||||
|
||||
if (decrypt == 0)
|
||||
return kem_cms_encrypt(ri);
|
||||
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
|
||||
return 0;
|
||||
}
|
|
@ -0,0 +1,409 @@
|
|||
/*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#include <openssl/cms.h>
|
||||
#include <openssl/core_names.h>
|
||||
#include <openssl/crypto.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/evp.h>
|
||||
#include <openssl/kdf.h>
|
||||
#include <openssl/x509.h>
|
||||
#include "cms_local.h"
|
||||
#include "crypto/evp.h"
|
||||
#include "internal/sizes.h"
|
||||
|
||||
/* KEM Recipient Info (KEMRI) routines */
|
||||
|
||||
int ossl_cms_RecipientInfo_kemri_get0_alg(CMS_RecipientInfo *ri,
|
||||
uint32_t **pkekLength,
|
||||
X509_ALGOR **pwrap)
|
||||
{
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return 0;
|
||||
}
|
||||
if (pkekLength)
|
||||
*pkekLength = &ri->d.ori->d.kemri->kekLength;
|
||||
if (pwrap)
|
||||
*pwrap = ri->d.ori->d.kemri->wrap;
|
||||
return 1;
|
||||
}
|
||||
|
||||
int CMS_RecipientInfo_kemri_cert_cmp(CMS_RecipientInfo *ri, X509 *cert)
|
||||
{
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return -2;
|
||||
}
|
||||
return ossl_cms_SignerIdentifier_cert_cmp(ri->d.ori->d.kemri->rid, cert);
|
||||
}
|
||||
|
||||
int CMS_RecipientInfo_kemri_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pk)
|
||||
{
|
||||
EVP_PKEY_CTX *pctx = NULL;
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return 0;
|
||||
}
|
||||
|
||||
kemri = ri->d.ori->d.kemri;
|
||||
|
||||
EVP_PKEY_CTX_free(kemri->pctx);
|
||||
kemri->pctx = NULL;
|
||||
|
||||
if (pk != NULL) {
|
||||
pctx = EVP_PKEY_CTX_new_from_pkey(ossl_cms_ctx_get0_libctx(kemri->cms_ctx), pk,
|
||||
ossl_cms_ctx_get0_propq(kemri->cms_ctx));
|
||||
if (pctx == NULL || EVP_PKEY_decapsulate_init(pctx, NULL) <= 0)
|
||||
goto err;
|
||||
|
||||
kemri->pctx = pctx;
|
||||
}
|
||||
|
||||
return 1;
|
||||
err:
|
||||
EVP_PKEY_CTX_free(pctx);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Initialise a kemri based on passed certificate and key */
|
||||
|
||||
int ossl_cms_RecipientInfo_kemri_init(CMS_RecipientInfo *ri, X509 *recip,
|
||||
EVP_PKEY *recipPubKey, unsigned int flags,
|
||||
const CMS_CTX *ctx)
|
||||
{
|
||||
CMS_OtherRecipientInfo *ori;
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
int idtype;
|
||||
X509_PUBKEY *x_pubkey;
|
||||
X509_ALGOR *x_alg;
|
||||
|
||||
ri->d.ori = M_ASN1_new_of(CMS_OtherRecipientInfo);
|
||||
if (ri->d.ori == NULL)
|
||||
return 0;
|
||||
ri->encoded_type = CMS_RECIPINFO_OTHER;
|
||||
ri->type = CMS_RECIPINFO_KEM;
|
||||
|
||||
ori = ri->d.ori;
|
||||
ori->oriType = OBJ_nid2obj(NID_id_smime_ori_kem);
|
||||
if (ori->oriType == NULL)
|
||||
return 0;
|
||||
ori->d.kemri = M_ASN1_new_of(CMS_KEMRecipientInfo);
|
||||
if (ori->d.kemri == NULL)
|
||||
return 0;
|
||||
|
||||
kemri = ori->d.kemri;
|
||||
kemri->version = 0;
|
||||
kemri->cms_ctx = ctx;
|
||||
|
||||
/*
|
||||
* Not a typo: RecipientIdentifier and SignerIdentifier are the same
|
||||
* structure.
|
||||
*/
|
||||
|
||||
idtype = (flags & CMS_USE_KEYID) ? CMS_RECIPINFO_KEYIDENTIFIER : CMS_RECIPINFO_ISSUER_SERIAL;
|
||||
if (!ossl_cms_set1_SignerIdentifier(kemri->rid, recip, idtype, ctx))
|
||||
return 0;
|
||||
|
||||
x_pubkey = X509_get_X509_PUBKEY(recip);
|
||||
if (x_pubkey == NULL)
|
||||
return 0;
|
||||
if (!X509_PUBKEY_get0_param(NULL, NULL, NULL, &x_alg, x_pubkey))
|
||||
return 0;
|
||||
if (!X509_ALGOR_copy(kemri->kem, x_alg))
|
||||
return 0;
|
||||
|
||||
kemri->pctx = EVP_PKEY_CTX_new_from_pkey(ossl_cms_ctx_get0_libctx(ctx),
|
||||
recipPubKey,
|
||||
ossl_cms_ctx_get0_propq(ctx));
|
||||
if (kemri->pctx == NULL)
|
||||
return 0;
|
||||
if (EVP_PKEY_encapsulate_init(kemri->pctx, NULL) <= 0)
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
EVP_CIPHER_CTX *CMS_RecipientInfo_kemri_get0_ctx(CMS_RecipientInfo *ri)
|
||||
{
|
||||
if (ri->type == CMS_RECIPINFO_KEM)
|
||||
return ri->d.ori->d.kemri->ctx;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
X509_ALGOR *CMS_RecipientInfo_kemri_get0_kdf_alg(CMS_RecipientInfo *ri)
|
||||
{
|
||||
if (ri->type == CMS_RECIPINFO_KEM)
|
||||
return ri->d.ori->d.kemri->kdf;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int CMS_RecipientInfo_kemri_set_ukm(CMS_RecipientInfo *ri,
|
||||
const unsigned char *ukm,
|
||||
int ukmLength)
|
||||
{
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (ukm == NULL && ukmLength != 0) {
|
||||
ERR_raise(ERR_LIB_CMS, ERR_R_PASSED_INVALID_ARGUMENT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
kemri = ri->d.ori->d.kemri;
|
||||
|
||||
ASN1_OCTET_STRING_free(kemri->ukm);
|
||||
kemri->ukm = ASN1_OCTET_STRING_new();
|
||||
if (kemri->ukm == NULL)
|
||||
return 0;
|
||||
ASN1_OCTET_STRING_set(kemri->ukm, ukm, ukmLength);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static EVP_KDF_CTX *create_kdf_ctx(CMS_KEMRecipientInfo *kemri)
|
||||
{
|
||||
const ASN1_OBJECT *kdf_oid;
|
||||
int ptype;
|
||||
char kdf_alg[OSSL_MAX_NAME_SIZE];
|
||||
EVP_KDF *kdf = NULL;
|
||||
EVP_KDF_CTX *kctx = NULL;
|
||||
|
||||
/*
|
||||
* KDFs with algorithm identifier parameters are not supported yet. To
|
||||
* support this, EVP_KDF_CTX_set_algor_params from
|
||||
* `doc/designs/passing-algorithmidentifier-parameters.md` needs to be
|
||||
* implemented.
|
||||
*/
|
||||
X509_ALGOR_get0(&kdf_oid, &ptype, NULL, kemri->kdf);
|
||||
if (ptype != V_ASN1_UNDEF && ptype != V_ASN1_NULL) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_KDF_ALGORITHM);
|
||||
goto err;
|
||||
}
|
||||
if (OBJ_obj2txt(kdf_alg, sizeof(kdf_alg), kdf_oid, 1) < 0)
|
||||
goto err;
|
||||
|
||||
kdf = EVP_KDF_fetch(ossl_cms_ctx_get0_libctx(kemri->cms_ctx), kdf_alg,
|
||||
ossl_cms_ctx_get0_propq(kemri->cms_ctx));
|
||||
if (kdf == NULL)
|
||||
goto err;
|
||||
|
||||
kctx = EVP_KDF_CTX_new(kdf);
|
||||
err:
|
||||
EVP_KDF_free(kdf);
|
||||
return kctx;
|
||||
}
|
||||
|
||||
static int kdf_derive(unsigned char *kek, size_t keklen,
|
||||
const unsigned char *ss, size_t sslen,
|
||||
CMS_KEMRecipientInfo *kemri)
|
||||
{
|
||||
EVP_KDF_CTX *kctx = NULL;
|
||||
OSSL_PARAM params[3];
|
||||
unsigned char *infoder = NULL;
|
||||
int infolen = 0;
|
||||
int rv = 0;
|
||||
|
||||
infolen = CMS_CMSORIforKEMOtherInfo_encode(&infoder, kemri->wrap, kemri->ukm,
|
||||
kemri->kekLength);
|
||||
if (infolen <= 0)
|
||||
goto err;
|
||||
|
||||
kctx = create_kdf_ctx(kemri);
|
||||
if (kctx == NULL)
|
||||
goto err;
|
||||
|
||||
params[0] = OSSL_PARAM_construct_octet_string(OSSL_KDF_PARAM_KEY,
|
||||
(unsigned char *)ss, sslen);
|
||||
params[1] = OSSL_PARAM_construct_octet_string(OSSL_KDF_PARAM_INFO,
|
||||
(char *)infoder, infolen);
|
||||
params[2] = OSSL_PARAM_construct_end();
|
||||
|
||||
if (EVP_KDF_derive(kctx, kek, keklen, params) <= 0)
|
||||
goto err;
|
||||
|
||||
rv = 1;
|
||||
err:
|
||||
OPENSSL_free(infoder);
|
||||
EVP_KDF_CTX_free(kctx);
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/*
|
||||
* Derive KEK and decrypt/encrypt with it to produce either the original CEK
|
||||
* or the encrypted CEK.
|
||||
*/
|
||||
|
||||
static int cms_kek_cipher(unsigned char **pout, size_t *poutlen,
|
||||
const unsigned char *ss, size_t sslen,
|
||||
const unsigned char *in, size_t inlen,
|
||||
CMS_KEMRecipientInfo *kemri, int enc)
|
||||
{
|
||||
/* Key encryption key */
|
||||
unsigned char kek[EVP_MAX_KEY_LENGTH];
|
||||
size_t keklen = kemri->kekLength;
|
||||
unsigned char *out = NULL;
|
||||
int outlen = 0;
|
||||
int rv = 0;
|
||||
|
||||
if (keklen > sizeof(kek)) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_INVALID_KEY_LENGTH);
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (!kdf_derive(kek, keklen, ss, sslen, kemri))
|
||||
goto err;
|
||||
|
||||
/* Set KEK in context */
|
||||
if (!EVP_CipherInit_ex(kemri->ctx, NULL, NULL, kek, NULL, enc))
|
||||
goto err;
|
||||
/* obtain output length of ciphered key */
|
||||
if (!EVP_CipherUpdate(kemri->ctx, NULL, &outlen, in, (int)inlen))
|
||||
goto err;
|
||||
out = OPENSSL_malloc(outlen);
|
||||
if (out == NULL)
|
||||
goto err;
|
||||
if (!EVP_CipherUpdate(kemri->ctx, out, &outlen, in, (int)inlen))
|
||||
goto err;
|
||||
*pout = out;
|
||||
out = NULL;
|
||||
*poutlen = (size_t)outlen;
|
||||
|
||||
rv = 1;
|
||||
err:
|
||||
OPENSSL_free(out);
|
||||
OPENSSL_cleanse(kek, keklen);
|
||||
EVP_CIPHER_CTX_reset(kemri->ctx);
|
||||
EVP_PKEY_CTX_free(kemri->pctx);
|
||||
kemri->pctx = NULL;
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* Encrypt content key in KEM recipient info */
|
||||
|
||||
int ossl_cms_RecipientInfo_kemri_encrypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri)
|
||||
{
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
CMS_EncryptedContentInfo *ec;
|
||||
unsigned char *kem_ct = NULL;
|
||||
size_t kem_ct_len;
|
||||
unsigned char *kem_secret = NULL;
|
||||
size_t kem_secret_len = 0;
|
||||
unsigned char *enckey;
|
||||
size_t enckeylen;
|
||||
int rv = 0;
|
||||
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return 0;
|
||||
}
|
||||
|
||||
kemri = ri->d.ori->d.kemri;
|
||||
|
||||
ec = ossl_cms_get0_env_enc_content(cms);
|
||||
/* Initialise wrap algorithm parameters */
|
||||
if (!ossl_cms_RecipientInfo_wrap_init(ri, ec->cipher))
|
||||
return 0;
|
||||
|
||||
/* Initialise KDF algorithm */
|
||||
if (!ossl_cms_env_asn1_ctrl(ri, 0))
|
||||
return 0;
|
||||
|
||||
if (EVP_PKEY_encapsulate(kemri->pctx, NULL, &kem_ct_len, NULL, &kem_secret_len) <= 0)
|
||||
return 0;
|
||||
kem_ct = OPENSSL_malloc(kem_ct_len);
|
||||
kem_secret = OPENSSL_malloc(kem_secret_len);
|
||||
if (kem_ct == NULL || kem_secret == NULL)
|
||||
goto err;
|
||||
|
||||
if (EVP_PKEY_encapsulate(kemri->pctx, kem_ct, &kem_ct_len, kem_secret, &kem_secret_len) <= 0)
|
||||
goto err;
|
||||
|
||||
ASN1_STRING_set0(kemri->kemct, kem_ct, (int)kem_ct_len);
|
||||
kem_ct = NULL;
|
||||
|
||||
if (!cms_kek_cipher(&enckey, &enckeylen, kem_secret, kem_secret_len, ec->key, ec->keylen,
|
||||
kemri, 1))
|
||||
goto err;
|
||||
ASN1_STRING_set0(kemri->encryptedKey, enckey, (int)enckeylen);
|
||||
|
||||
rv = 1;
|
||||
err:
|
||||
OPENSSL_free(kem_ct);
|
||||
OPENSSL_clear_free(kem_secret, kem_secret_len);
|
||||
return rv;
|
||||
}
|
||||
|
||||
int ossl_cms_RecipientInfo_kemri_decrypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri)
|
||||
{
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
CMS_EncryptedContentInfo *ec;
|
||||
const unsigned char *kem_ct = NULL;
|
||||
size_t kem_ct_len;
|
||||
unsigned char *kem_secret = NULL;
|
||||
size_t kem_secret_len = 0;
|
||||
unsigned char *enckey = NULL;
|
||||
size_t enckeylen;
|
||||
unsigned char *cek = NULL;
|
||||
size_t ceklen;
|
||||
int ret = 0;
|
||||
|
||||
if (ri->type != CMS_RECIPINFO_KEM) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NOT_KEM);
|
||||
return 0;
|
||||
}
|
||||
|
||||
kemri = ri->d.ori->d.kemri;
|
||||
|
||||
ec = ossl_cms_get0_env_enc_content(cms);
|
||||
|
||||
if (kemri->pctx == NULL) {
|
||||
ERR_raise(ERR_LIB_CMS, CMS_R_NO_PRIVATE_KEY);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Setup all parameters to derive KEK */
|
||||
if (!ossl_cms_env_asn1_ctrl(ri, 1))
|
||||
goto err;
|
||||
|
||||
kem_ct = ASN1_STRING_get0_data(kemri->kemct);
|
||||
kem_ct_len = ASN1_STRING_length(kemri->kemct);
|
||||
|
||||
if (EVP_PKEY_decapsulate(kemri->pctx, NULL, &kem_secret_len, kem_ct, kem_ct_len) <= 0)
|
||||
return 0;
|
||||
kem_secret = OPENSSL_malloc(kem_secret_len);
|
||||
if (kem_secret == NULL)
|
||||
goto err;
|
||||
|
||||
if (EVP_PKEY_decapsulate(kemri->pctx, kem_secret, &kem_secret_len, kem_ct, kem_ct_len) <= 0)
|
||||
goto err;
|
||||
|
||||
/* Attempt to decrypt CEK */
|
||||
enckeylen = kemri->encryptedKey->length;
|
||||
enckey = kemri->encryptedKey->data;
|
||||
if (!cms_kek_cipher(&cek, &ceklen, kem_secret, kem_secret_len, enckey, enckeylen, kemri, 0))
|
||||
goto err;
|
||||
ec = ossl_cms_get0_env_enc_content(cms);
|
||||
OPENSSL_clear_free(ec->key, ec->keylen);
|
||||
ec->key = cek;
|
||||
ec->keylen = ceklen;
|
||||
|
||||
ret = 1;
|
||||
err:
|
||||
OPENSSL_clear_free(kem_secret, kem_secret_len);
|
||||
return ret;
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright 2008-2024 The OpenSSL Project Authors. All Rights Reserved.
|
||||
* Copyright 2008-2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
|
@ -41,6 +41,7 @@ typedef struct CMS_KEKIdentifier_st CMS_KEKIdentifier;
|
|||
typedef struct CMS_KEKRecipientInfo_st CMS_KEKRecipientInfo;
|
||||
typedef struct CMS_PasswordRecipientInfo_st CMS_PasswordRecipientInfo;
|
||||
typedef struct CMS_OtherRecipientInfo_st CMS_OtherRecipientInfo;
|
||||
typedef struct CMS_KEMRecipientInfo_st CMS_KEMRecipientInfo;
|
||||
typedef struct CMS_ReceiptsFrom_st CMS_ReceiptsFrom;
|
||||
typedef struct CMS_CTX_st CMS_CTX;
|
||||
|
||||
|
@ -142,7 +143,11 @@ struct CMS_EncryptedContentInfo_st {
|
|||
};
|
||||
|
||||
struct CMS_RecipientInfo_st {
|
||||
int type;
|
||||
/*
|
||||
* Type which the RecipientInfo is encoded with. OtherRecipientInfo
|
||||
* encompasses different types, specified by 'type' below.
|
||||
*/
|
||||
int encoded_type;
|
||||
union {
|
||||
CMS_KeyTransRecipientInfo *ktri;
|
||||
CMS_KeyAgreeRecipientInfo *kari;
|
||||
|
@ -150,6 +155,8 @@ struct CMS_RecipientInfo_st {
|
|||
CMS_PasswordRecipientInfo *pwri;
|
||||
CMS_OtherRecipientInfo *ori;
|
||||
} d;
|
||||
/* internal type, including ORI types */
|
||||
int type;
|
||||
};
|
||||
|
||||
typedef CMS_SignerIdentifier CMS_RecipientIdentifier;
|
||||
|
@ -245,7 +252,29 @@ struct CMS_PasswordRecipientInfo_st {
|
|||
|
||||
struct CMS_OtherRecipientInfo_st {
|
||||
ASN1_OBJECT *oriType;
|
||||
ASN1_TYPE *oriValue;
|
||||
union {
|
||||
/* NID_id_smime_ori_kem */
|
||||
CMS_KEMRecipientInfo *kemri;
|
||||
/* anything else */
|
||||
ASN1_TYPE *other;
|
||||
} d;
|
||||
};
|
||||
|
||||
struct CMS_KEMRecipientInfo_st {
|
||||
int32_t version;
|
||||
CMS_RecipientIdentifier *rid;
|
||||
X509_ALGOR *kem;
|
||||
ASN1_OCTET_STRING *kemct;
|
||||
X509_ALGOR *kdf;
|
||||
uint32_t kekLength;
|
||||
ASN1_OCTET_STRING *ukm;
|
||||
X509_ALGOR *wrap;
|
||||
ASN1_OCTET_STRING *encryptedKey;
|
||||
/* Public key context associated with current operation */
|
||||
EVP_PKEY_CTX *pctx;
|
||||
/* Cipher context for CEK wrapping */
|
||||
EVP_CIPHER_CTX *ctx;
|
||||
const CMS_CTX *cms_ctx;
|
||||
};
|
||||
|
||||
struct CMS_DigestedData_st {
|
||||
|
@ -460,6 +489,7 @@ int ossl_cms_pkey_get_ri_type(EVP_PKEY *pk);
|
|||
int ossl_cms_pkey_is_ri_type_supported(EVP_PKEY *pk, int ri_type);
|
||||
|
||||
void ossl_cms_RecipientInfos_set_cmsctx(CMS_ContentInfo *cms);
|
||||
int ossl_cms_RecipientInfo_wrap_init(CMS_RecipientInfo *ri, const EVP_CIPHER *cipher);
|
||||
|
||||
/* KARI routines */
|
||||
int ossl_cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
|
||||
|
@ -470,6 +500,20 @@ int ossl_cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
|
|||
int ossl_cms_RecipientInfo_kari_encrypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri);
|
||||
|
||||
/* KEMRI routines */
|
||||
int ossl_cms_RecipientInfo_kemri_get0_alg(CMS_RecipientInfo *ri,
|
||||
uint32_t **pkekLength,
|
||||
X509_ALGOR **pwrap);
|
||||
int ossl_cms_RecipientInfo_kemri_init(CMS_RecipientInfo *ri, X509 *recip,
|
||||
EVP_PKEY *recipPubKey, unsigned int flags,
|
||||
const CMS_CTX *ctx);
|
||||
int ossl_cms_RecipientInfo_kemri_encrypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri);
|
||||
int ossl_cms_RecipientInfo_kemri_decrypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri);
|
||||
int CMS_CMSORIforKEMOtherInfo_encode(unsigned char **pder, X509_ALGOR *wrap,
|
||||
ASN1_OCTET_STRING *ukm, int keylen);
|
||||
|
||||
/* PWRI routines */
|
||||
int ossl_cms_RecipientInfo_pwri_crypt(const CMS_ContentInfo *cms,
|
||||
CMS_RecipientInfo *ri, int en_de);
|
||||
|
@ -486,6 +530,7 @@ int ossl_cms_dh_envelope(CMS_RecipientInfo *ri, int decrypt);
|
|||
int ossl_cms_ecdh_envelope(CMS_RecipientInfo *ri, int decrypt);
|
||||
int ossl_cms_rsa_envelope(CMS_RecipientInfo *ri, int decrypt);
|
||||
int ossl_cms_rsa_sign(CMS_SignerInfo *si, int verify);
|
||||
int ossl_cms_kem_envelope(CMS_RecipientInfo *ri, int decrypt);
|
||||
|
||||
int ossl_cms_get1_certs_ex(CMS_ContentInfo *cms, STACK_OF(X509) **certs);
|
||||
int ossl_cms_get1_crls_ex(CMS_ContentInfo *cms, STACK_OF(X509_CRL) **crls);
|
||||
|
@ -496,10 +541,12 @@ DECLARE_ASN1_ITEM(CMS_EncryptedData)
|
|||
DECLARE_ASN1_ITEM(CMS_EnvelopedData)
|
||||
DECLARE_ASN1_ITEM(CMS_AuthEnvelopedData)
|
||||
DECLARE_ASN1_ITEM(CMS_KEKRecipientInfo)
|
||||
DECLARE_ASN1_ITEM(CMS_KEMRecipientInfo)
|
||||
DECLARE_ASN1_ITEM(CMS_KeyAgreeRecipientInfo)
|
||||
DECLARE_ASN1_ITEM(CMS_KeyTransRecipientInfo)
|
||||
DECLARE_ASN1_ITEM(CMS_OriginatorPublicKey)
|
||||
DECLARE_ASN1_ITEM(CMS_OtherKeyAttribute)
|
||||
DECLARE_ASN1_ITEM(CMS_OtherRecipientInfo)
|
||||
DECLARE_ASN1_ITEM(CMS_Receipt)
|
||||
DECLARE_ASN1_ITEM(CMS_ReceiptRequest)
|
||||
DECLARE_ASN1_ITEM(CMS_RecipientEncryptedKey)
|
||||
|
|
|
@ -138,7 +138,7 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms,
|
|||
ERR_raise(ERR_LIB_CMS, ERR_R_ASN1_LIB);
|
||||
goto err;
|
||||
}
|
||||
ri->type = CMS_RECIPINFO_PASS;
|
||||
ri->encoded_type = ri->type = CMS_RECIPINFO_PASS;
|
||||
|
||||
pwri = ri->d.pwri;
|
||||
pwri->cms_ctx = cms_ctx;
|
||||
|
|
|
@ -750,6 +750,14 @@ int CMS_decrypt_set1_pkey_and_peer(CMS_ContentInfo *cms, EVP_PKEY *pk,
|
|||
return 1;
|
||||
if (r < 0)
|
||||
return 0;
|
||||
} else if (ri_type == CMS_RECIPINFO_KEM) {
|
||||
if (cert == NULL || !CMS_RecipientInfo_kemri_cert_cmp(ri, cert)) {
|
||||
CMS_RecipientInfo_kemri_set0_pkey(ri, pk);
|
||||
r = CMS_RecipientInfo_decrypt(cms, ri);
|
||||
CMS_RecipientInfo_kemri_set0_pkey(ri, NULL);
|
||||
if (cert != NULL || r > 0)
|
||||
return r;
|
||||
}
|
||||
}
|
||||
/* If we have a cert, try matching RecipientInfo, else try them all */
|
||||
else if (cert == NULL || !CMS_RecipientInfo_ktri_cert_cmp(ri, cert)) {
|
||||
|
|
|
@ -354,6 +354,7 @@ CMS_R_NEED_ONE_SIGNER:164:need one signer
|
|||
CMS_R_NOT_A_SIGNED_RECEIPT:165:not a signed receipt
|
||||
CMS_R_NOT_ENCRYPTED_DATA:122:not encrypted data
|
||||
CMS_R_NOT_KEK:123:not kek
|
||||
CMS_R_NOT_KEM:197:not kem
|
||||
CMS_R_NOT_KEY_AGREEMENT:181:not key agreement
|
||||
CMS_R_NOT_KEY_TRANSPORT:124:not key transport
|
||||
CMS_R_NOT_PWRI:177:not pwri
|
||||
|
@ -394,11 +395,13 @@ CMS_R_UNABLE_TO_FINALIZE_CONTEXT:147:unable to finalize context
|
|||
CMS_R_UNKNOWN_CIPHER:148:unknown cipher
|
||||
CMS_R_UNKNOWN_DIGEST_ALGORITHM:149:unknown digest algorithm
|
||||
CMS_R_UNKNOWN_ID:150:unknown id
|
||||
CMS_R_UNKNOWN_KDF_ALGORITHM:198:unknown kdf algorithm
|
||||
CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM:151:unsupported compression algorithm
|
||||
CMS_R_UNSUPPORTED_CONTENT_ENCRYPTION_ALGORITHM:194:\
|
||||
unsupported content encryption algorithm
|
||||
CMS_R_UNSUPPORTED_CONTENT_TYPE:152:unsupported content type
|
||||
CMS_R_UNSUPPORTED_ENCRYPTION_TYPE:192:unsupported encryption type
|
||||
CMS_R_UNSUPPORTED_KDF_ALGORITHM:199:unsupported kdf algorithm
|
||||
CMS_R_UNSUPPORTED_KEK_ALGORITHM:153:unsupported kek algorithm
|
||||
CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM:179:\
|
||||
unsupported key encryption algorithm
|
||||
|
|
|
@ -434,6 +434,10 @@ int EVP_DigestSignUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize)
|
|||
|
||||
legacy:
|
||||
if (pctx != NULL) {
|
||||
if (pctx->pmeth == NULL) {
|
||||
ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR);
|
||||
return 0;
|
||||
}
|
||||
/* do_sigver_init() checked that |digest_custom| is non-NULL */
|
||||
if (pctx->flag_call_digest_custom
|
||||
&& !ctx->pctx->pmeth->digest_custom(ctx->pctx, ctx))
|
||||
|
|
|
@ -37,13 +37,16 @@ struct added_obj_st {
|
|||
ASN1_OBJECT *obj;
|
||||
};
|
||||
|
||||
static unsigned long added_obj_hash(const ADDED_OBJ *ca);
|
||||
static int added_obj_cmp(const ADDED_OBJ *ca, const ADDED_OBJ *cb);
|
||||
|
||||
static LHASH_OF(ADDED_OBJ) *added = NULL;
|
||||
static CRYPTO_RWLOCK *ossl_obj_lock = NULL;
|
||||
#ifdef TSAN_REQUIRES_LOCKING
|
||||
static CRYPTO_RWLOCK *ossl_obj_nid_lock = NULL;
|
||||
#endif
|
||||
|
||||
static CRYPTO_ONCE ossl_obj_lock_init = CRYPTO_ONCE_STATIC_INIT;
|
||||
static CRYPTO_ONCE ossl_obj_api_init = CRYPTO_ONCE_STATIC_INIT;
|
||||
|
||||
static ossl_inline void objs_free_locks(void)
|
||||
{
|
||||
|
@ -55,7 +58,7 @@ static ossl_inline void objs_free_locks(void)
|
|||
#endif
|
||||
}
|
||||
|
||||
DEFINE_RUN_ONCE_STATIC(obj_lock_initialise)
|
||||
DEFINE_RUN_ONCE_STATIC(obj_api_initialise)
|
||||
{
|
||||
ossl_obj_lock = CRYPTO_THREAD_lock_new();
|
||||
if (ossl_obj_lock == NULL)
|
||||
|
@ -68,39 +71,40 @@ DEFINE_RUN_ONCE_STATIC(obj_lock_initialise)
|
|||
return 0;
|
||||
}
|
||||
#endif
|
||||
added = lh_ADDED_OBJ_new(added_obj_hash, added_obj_cmp);
|
||||
if (added == NULL) {
|
||||
objs_free_locks();
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static ossl_inline int ossl_init_added_lock(void)
|
||||
static ossl_inline int ossl_init_added_api(void)
|
||||
{
|
||||
#ifndef OPENSSL_NO_AUTOLOAD_CONFIG
|
||||
/* Make sure we've loaded config before checking for any "added" objects */
|
||||
OPENSSL_init_crypto(OPENSSL_INIT_LOAD_CONFIG, NULL);
|
||||
#endif
|
||||
return RUN_ONCE(&ossl_obj_lock_init, obj_lock_initialise);
|
||||
return RUN_ONCE(&ossl_obj_api_init, obj_api_initialise);
|
||||
}
|
||||
|
||||
static ossl_inline int ossl_obj_write_lock(int lock)
|
||||
static ossl_inline int ossl_obj_write_lock(void)
|
||||
{
|
||||
if (!lock)
|
||||
return 1;
|
||||
if (!ossl_init_added_lock())
|
||||
if (!ossl_init_added_api())
|
||||
return 0;
|
||||
return CRYPTO_THREAD_write_lock(ossl_obj_lock);
|
||||
}
|
||||
|
||||
static ossl_inline int ossl_obj_read_lock(int lock)
|
||||
static ossl_inline int ossl_obj_read_lock(void)
|
||||
{
|
||||
if (!lock)
|
||||
return 1;
|
||||
if (!ossl_init_added_lock())
|
||||
if (!ossl_init_added_api())
|
||||
return 0;
|
||||
return CRYPTO_THREAD_read_lock(ossl_obj_lock);
|
||||
}
|
||||
|
||||
static ossl_inline void ossl_obj_unlock(int lock)
|
||||
static ossl_inline void ossl_obj_unlock(void)
|
||||
{
|
||||
if (lock)
|
||||
CRYPTO_THREAD_unlock(ossl_obj_lock);
|
||||
}
|
||||
|
||||
|
@ -221,112 +225,22 @@ void ossl_obj_cleanup_int(void)
|
|||
objs_free_locks();
|
||||
}
|
||||
|
||||
/*
|
||||
* Requires that the ossl_obj_lock be held
|
||||
* if TSAN_REQUIRES_LOCKING defined
|
||||
*/
|
||||
static int obj_new_nid_unlocked(int num)
|
||||
int OBJ_new_nid(int num)
|
||||
{
|
||||
static TSAN_QUALIFIER int new_nid = NUM_NID;
|
||||
#ifdef TSAN_REQUIRES_LOCKING
|
||||
int i;
|
||||
|
||||
ossl_obj_write_lock();
|
||||
i = new_nid;
|
||||
new_nid += num;
|
||||
|
||||
ossl_obj_unlock();
|
||||
return i;
|
||||
#else
|
||||
return tsan_add(&new_nid, num);
|
||||
#endif
|
||||
}
|
||||
|
||||
int OBJ_new_nid(int num)
|
||||
{
|
||||
#ifdef TSAN_REQUIRES_LOCKING
|
||||
int i;
|
||||
|
||||
if (!ossl_obj_write_lock(1)) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_WRITE_LOCK);
|
||||
return NID_undef;
|
||||
}
|
||||
|
||||
i = obj_new_nid_unlocked(num);
|
||||
|
||||
ossl_obj_unlock(1);
|
||||
|
||||
return i;
|
||||
#else
|
||||
return obj_new_nid_unlocked(num);
|
||||
#endif
|
||||
}
|
||||
|
||||
static int ossl_obj_add_object(const ASN1_OBJECT *obj, int lock)
|
||||
{
|
||||
ASN1_OBJECT *o = NULL;
|
||||
ADDED_OBJ *ao[4] = { NULL, NULL, NULL, NULL }, *aop[4];
|
||||
int i;
|
||||
|
||||
if ((o = OBJ_dup(obj)) == NULL)
|
||||
return NID_undef;
|
||||
if ((ao[ADDED_NID] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL
|
||||
|| (o->length != 0
|
||||
&& obj->data != NULL
|
||||
&& (ao[ADDED_DATA] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL)
|
||||
|| (o->sn != NULL
|
||||
&& (ao[ADDED_SNAME] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL)
|
||||
|| (o->ln != NULL
|
||||
&& (ao[ADDED_LNAME] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL))
|
||||
goto err2;
|
||||
|
||||
if (!ossl_obj_write_lock(lock)) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_WRITE_LOCK);
|
||||
goto err2;
|
||||
}
|
||||
if (added == NULL) {
|
||||
added = lh_ADDED_OBJ_new(added_obj_hash, added_obj_cmp);
|
||||
if (added == NULL) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_CRYPTO_LIB);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = ADDED_DATA; i <= ADDED_NID; i++) {
|
||||
if (ao[i] != NULL) {
|
||||
ao[i]->type = i;
|
||||
ao[i]->obj = o;
|
||||
aop[i] = lh_ADDED_OBJ_retrieve(added, ao[i]);
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = -1;
|
||||
(void)lh_ADDED_OBJ_insert(added, ao[i]);
|
||||
if (lh_ADDED_OBJ_error(added)) {
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = i;
|
||||
while (i-- > ADDED_DATA) {
|
||||
lh_ADDED_OBJ_delete(added, ao[i]);
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = i;
|
||||
}
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_CRYPTO_LIB);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
}
|
||||
o->flags &=
|
||||
~(ASN1_OBJECT_FLAG_DYNAMIC | ASN1_OBJECT_FLAG_DYNAMIC_STRINGS |
|
||||
ASN1_OBJECT_FLAG_DYNAMIC_DATA);
|
||||
|
||||
ossl_obj_unlock(lock);
|
||||
return o->nid;
|
||||
|
||||
err:
|
||||
ossl_obj_unlock(lock);
|
||||
err2:
|
||||
for (i = ADDED_DATA; i <= ADDED_NID; i++)
|
||||
OPENSSL_free(ao[i]);
|
||||
ASN1_OBJECT_free(o);
|
||||
return NID_undef;
|
||||
}
|
||||
|
||||
ASN1_OBJECT *OBJ_nid2obj(int n)
|
||||
{
|
||||
ADDED_OBJ ad, *adp = NULL;
|
||||
|
@ -339,13 +253,12 @@ ASN1_OBJECT *OBJ_nid2obj(int n)
|
|||
ad.type = ADDED_NID;
|
||||
ad.obj = &ob;
|
||||
ob.nid = n;
|
||||
if (!ossl_obj_read_lock(1)) {
|
||||
if (!ossl_obj_read_lock()) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_READ_LOCK);
|
||||
return NULL;
|
||||
}
|
||||
if (added != NULL)
|
||||
adp = lh_ADDED_OBJ_retrieve(added, &ad);
|
||||
ossl_obj_unlock(1);
|
||||
ossl_obj_unlock();
|
||||
if (adp != NULL)
|
||||
return adp->obj;
|
||||
|
||||
|
@ -383,7 +296,7 @@ static int obj_cmp(const ASN1_OBJECT *const *ap, const unsigned int *bp)
|
|||
|
||||
IMPLEMENT_OBJ_BSEARCH_CMP_FN(const ASN1_OBJECT *, unsigned int, obj);
|
||||
|
||||
static int ossl_obj_obj2nid(const ASN1_OBJECT *a, const int lock)
|
||||
static int ossl_obj_obj2nid(const ASN1_OBJECT *a)
|
||||
{
|
||||
int nid = NID_undef;
|
||||
const unsigned int *op;
|
||||
|
@ -399,18 +312,16 @@ static int ossl_obj_obj2nid(const ASN1_OBJECT *a, const int lock)
|
|||
op = OBJ_bsearch_obj(&a, obj_objs, NUM_OBJ);
|
||||
if (op != NULL)
|
||||
return nid_objs[*op].nid;
|
||||
if (!ossl_obj_read_lock(lock)) {
|
||||
if (!ossl_obj_read_lock()) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_READ_LOCK);
|
||||
return NID_undef;
|
||||
}
|
||||
if (added != NULL) {
|
||||
ad.type = ADDED_DATA;
|
||||
ad.obj = (ASN1_OBJECT *)a; /* casting away const is harmless here */
|
||||
adp = lh_ADDED_OBJ_retrieve(added, &ad);
|
||||
if (adp != NULL)
|
||||
nid = adp->obj->nid;
|
||||
}
|
||||
ossl_obj_unlock(lock);
|
||||
ossl_obj_unlock();
|
||||
return nid;
|
||||
}
|
||||
|
||||
|
@ -645,18 +556,16 @@ int OBJ_ln2nid(const char *s)
|
|||
op = OBJ_bsearch_ln(&oo, ln_objs, NUM_LN);
|
||||
if (op != NULL)
|
||||
return nid_objs[*op].nid;
|
||||
if (!ossl_obj_read_lock(1)) {
|
||||
if (!ossl_obj_read_lock()) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_READ_LOCK);
|
||||
return NID_undef;
|
||||
}
|
||||
if (added != NULL) {
|
||||
ad.type = ADDED_LNAME;
|
||||
ad.obj = &o;
|
||||
adp = lh_ADDED_OBJ_retrieve(added, &ad);
|
||||
if (adp != NULL)
|
||||
nid = adp->obj->nid;
|
||||
}
|
||||
ossl_obj_unlock(1);
|
||||
ossl_obj_unlock();
|
||||
return nid;
|
||||
}
|
||||
|
||||
|
@ -672,18 +581,16 @@ int OBJ_sn2nid(const char *s)
|
|||
op = OBJ_bsearch_sn(&oo, sn_objs, NUM_SN);
|
||||
if (op != NULL)
|
||||
return nid_objs[*op].nid;
|
||||
if (!ossl_obj_read_lock(1)) {
|
||||
if (!ossl_obj_read_lock()) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_READ_LOCK);
|
||||
return NID_undef;
|
||||
}
|
||||
if (added != NULL) {
|
||||
ad.type = ADDED_SNAME;
|
||||
ad.obj = &o;
|
||||
adp = lh_ADDED_OBJ_retrieve(added, &ad);
|
||||
if (adp != NULL)
|
||||
nid = adp->obj->nid;
|
||||
}
|
||||
ossl_obj_unlock(1);
|
||||
ossl_obj_unlock();
|
||||
return nid;
|
||||
}
|
||||
|
||||
|
@ -808,20 +715,14 @@ int OBJ_create(const char *oid, const char *sn, const char *ln)
|
|||
}
|
||||
}
|
||||
|
||||
if (!ossl_obj_write_lock(1)) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_WRITE_LOCK);
|
||||
ASN1_OBJECT_free(tmpoid);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* If NID is not NID_undef then object already exists */
|
||||
if (oid != NULL
|
||||
&& ossl_obj_obj2nid(tmpoid, 0) != NID_undef) {
|
||||
&& ossl_obj_obj2nid(tmpoid) != NID_undef) {
|
||||
ERR_raise(ERR_LIB_OBJ, OBJ_R_OID_EXISTS);
|
||||
goto err;
|
||||
}
|
||||
|
||||
tmpoid->nid = obj_new_nid_unlocked(1);
|
||||
tmpoid->nid = OBJ_new_nid(1);
|
||||
|
||||
if (tmpoid->nid == NID_undef)
|
||||
goto err;
|
||||
|
@ -829,13 +730,14 @@ int OBJ_create(const char *oid, const char *sn, const char *ln)
|
|||
tmpoid->sn = (char *)sn;
|
||||
tmpoid->ln = (char *)ln;
|
||||
|
||||
ok = ossl_obj_add_object(tmpoid, 0);
|
||||
if (OBJ_add_object(tmpoid) != NID_undef)
|
||||
ok = 1;
|
||||
|
||||
|
||||
tmpoid->sn = NULL;
|
||||
tmpoid->ln = NULL;
|
||||
|
||||
err:
|
||||
ossl_obj_unlock(1);
|
||||
ASN1_OBJECT_free(tmpoid);
|
||||
return ok;
|
||||
}
|
||||
|
@ -856,10 +758,65 @@ const unsigned char *OBJ_get0_data(const ASN1_OBJECT *obj)
|
|||
|
||||
int OBJ_add_object(const ASN1_OBJECT *obj)
|
||||
{
|
||||
return ossl_obj_add_object(obj, 1);
|
||||
ASN1_OBJECT *o = NULL;
|
||||
ADDED_OBJ *ao[4] = { NULL, NULL, NULL, NULL }, *aop[4];
|
||||
int i;
|
||||
|
||||
if ((o = OBJ_dup(obj)) == NULL)
|
||||
return NID_undef;
|
||||
if ((ao[ADDED_NID] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL
|
||||
|| (o->length != 0
|
||||
&& obj->data != NULL
|
||||
&& (ao[ADDED_DATA] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL)
|
||||
|| (o->sn != NULL
|
||||
&& (ao[ADDED_SNAME] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL)
|
||||
|| (o->ln != NULL
|
||||
&& (ao[ADDED_LNAME] = OPENSSL_malloc(sizeof(*ao[0]))) == NULL))
|
||||
goto err2;
|
||||
|
||||
if (!ossl_obj_write_lock()) {
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_UNABLE_TO_GET_WRITE_LOCK);
|
||||
goto err2;
|
||||
}
|
||||
|
||||
for (i = ADDED_DATA; i <= ADDED_NID; i++) {
|
||||
if (ao[i] != NULL) {
|
||||
ao[i]->type = i;
|
||||
ao[i]->obj = o;
|
||||
aop[i] = lh_ADDED_OBJ_retrieve(added, ao[i]);
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = -1;
|
||||
(void)lh_ADDED_OBJ_insert(added, ao[i]);
|
||||
if (lh_ADDED_OBJ_error(added)) {
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = i;
|
||||
while (i-- > ADDED_DATA) {
|
||||
lh_ADDED_OBJ_delete(added, ao[i]);
|
||||
if (aop[i] != NULL)
|
||||
aop[i]->type = i;
|
||||
}
|
||||
ERR_raise(ERR_LIB_OBJ, ERR_R_CRYPTO_LIB);
|
||||
goto err;
|
||||
}
|
||||
}
|
||||
}
|
||||
o->flags &=
|
||||
~(ASN1_OBJECT_FLAG_DYNAMIC | ASN1_OBJECT_FLAG_DYNAMIC_STRINGS |
|
||||
ASN1_OBJECT_FLAG_DYNAMIC_DATA);
|
||||
|
||||
ossl_obj_unlock();
|
||||
return o->nid;
|
||||
|
||||
err:
|
||||
ossl_obj_unlock();
|
||||
err2:
|
||||
for (i = ADDED_DATA; i <= ADDED_NID; i++)
|
||||
OPENSSL_free(ao[i]);
|
||||
ASN1_OBJECT_free(o);
|
||||
return NID_undef;
|
||||
}
|
||||
|
||||
int OBJ_obj2nid(const ASN1_OBJECT *a)
|
||||
{
|
||||
return ossl_obj_obj2nid(a, 1);
|
||||
return ossl_obj_obj2nid(a);
|
||||
}
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
*/
|
||||
|
||||
/* Serialized OID's */
|
||||
static const unsigned char so[9550] = {
|
||||
static const unsigned char so[9571] = {
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D, /* [ 0] OBJ_rsadsi */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01, /* [ 6] OBJ_pkcs */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x02,0x02, /* [ 13] OBJ_md2 */
|
||||
|
@ -1351,9 +1351,11 @@ static const unsigned char so[9550] = {
|
|||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x03,0x1C, /* [ 9516] OBJ_HKDF_SHA256 */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x03,0x1D, /* [ 9527] OBJ_HKDF_SHA384 */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x03,0x1E, /* [ 9538] OBJ_HKDF_SHA512 */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x0D, /* [ 9549] OBJ_id_smime_ori */
|
||||
0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x0D,0x03, /* [ 9559] OBJ_id_smime_ori_kem */
|
||||
};
|
||||
|
||||
#define NUM_NID 1499
|
||||
#define NUM_NID 1501
|
||||
static const ASN1_OBJECT nid_objs[NUM_NID] = {
|
||||
{"UNDEF", "undefined", NID_undef},
|
||||
{"rsadsi", "RSA Data Security, Inc.", NID_rsadsi, 6, &so[0]},
|
||||
|
@ -2854,9 +2856,11 @@ static const ASN1_OBJECT nid_objs[NUM_NID] = {
|
|||
{"id-alg-hkdf-with-sha256", "HKDF-SHA256", NID_HKDF_SHA256, 11, &so[9516]},
|
||||
{"id-alg-hkdf-with-sha384", "HKDF-SHA384", NID_HKDF_SHA384, 11, &so[9527]},
|
||||
{"id-alg-hkdf-with-sha512", "HKDF-SHA512", NID_HKDF_SHA512, 11, &so[9538]},
|
||||
{"id-smime-ori", "id-smime-ori", NID_id_smime_ori, 10, &so[9549]},
|
||||
{"id-smime-ori-kem", "id-smime-ori-kem", NID_id_smime_ori_kem, 11, &so[9559]},
|
||||
};
|
||||
|
||||
#define NUM_SN 1490
|
||||
#define NUM_SN 1492
|
||||
static const unsigned int sn_objs[NUM_SN] = {
|
||||
364, /* "AD_DVCS" */
|
||||
419, /* "AES-128-CBC" */
|
||||
|
@ -3744,6 +3748,8 @@ static const unsigned int sn_objs[NUM_SN] = {
|
|||
201, /* "id-smime-mod-ets-eSignature-97" */
|
||||
199, /* "id-smime-mod-msg-v3" */
|
||||
198, /* "id-smime-mod-oid" */
|
||||
1499, /* "id-smime-ori" */
|
||||
1500, /* "id-smime-ori-kem" */
|
||||
194, /* "id-smime-spq" */
|
||||
250, /* "id-smime-spq-ets-sqt-unotice" */
|
||||
249, /* "id-smime-spq-ets-sqt-uri" */
|
||||
|
@ -4350,7 +4356,7 @@ static const unsigned int sn_objs[NUM_SN] = {
|
|||
1289, /* "zstd" */
|
||||
};
|
||||
|
||||
#define NUM_LN 1490
|
||||
#define NUM_LN 1492
|
||||
static const unsigned int ln_objs[NUM_LN] = {
|
||||
363, /* "AD Time Stamping" */
|
||||
405, /* "ANSI X9.62" */
|
||||
|
@ -5367,6 +5373,8 @@ static const unsigned int ln_objs[NUM_LN] = {
|
|||
201, /* "id-smime-mod-ets-eSignature-97" */
|
||||
199, /* "id-smime-mod-msg-v3" */
|
||||
198, /* "id-smime-mod-oid" */
|
||||
1499, /* "id-smime-ori" */
|
||||
1500, /* "id-smime-ori-kem" */
|
||||
194, /* "id-smime-spq" */
|
||||
250, /* "id-smime-spq-ets-sqt-unotice" */
|
||||
249, /* "id-smime-spq-ets-sqt-uri" */
|
||||
|
@ -5844,7 +5852,7 @@ static const unsigned int ln_objs[NUM_LN] = {
|
|||
125, /* "zlib compression" */
|
||||
};
|
||||
|
||||
#define NUM_OBJ 1347
|
||||
#define NUM_OBJ 1349
|
||||
static const unsigned int obj_objs[NUM_OBJ] = {
|
||||
0, /* OBJ_undef 0 */
|
||||
181, /* OBJ_iso 1 */
|
||||
|
@ -7051,6 +7059,7 @@ static const unsigned int obj_objs[NUM_OBJ] = {
|
|||
193, /* OBJ_id_smime_cd 1 2 840 113549 1 9 16 4 */
|
||||
194, /* OBJ_id_smime_spq 1 2 840 113549 1 9 16 5 */
|
||||
195, /* OBJ_id_smime_cti 1 2 840 113549 1 9 16 6 */
|
||||
1499, /* OBJ_id_smime_ori 1 2 840 113549 1 9 16 13 */
|
||||
158, /* OBJ_x509Certificate 1 2 840 113549 1 9 22 1 */
|
||||
159, /* OBJ_sdsiCertificate 1 2 840 113549 1 9 22 2 */
|
||||
160, /* OBJ_x509Crl 1 2 840 113549 1 9 23 1 */
|
||||
|
@ -7169,6 +7178,7 @@ static const unsigned int obj_objs[NUM_OBJ] = {
|
|||
254, /* OBJ_id_smime_cti_ets_proofOfSender 1 2 840 113549 1 9 16 6 4 */
|
||||
255, /* OBJ_id_smime_cti_ets_proofOfApproval 1 2 840 113549 1 9 16 6 5 */
|
||||
256, /* OBJ_id_smime_cti_ets_proofOfCreation 1 2 840 113549 1 9 16 6 6 */
|
||||
1500, /* OBJ_id_smime_ori_kem 1 2 840 113549 1 9 16 13 3 */
|
||||
150, /* OBJ_keyBag 1 2 840 113549 1 12 10 1 1 */
|
||||
151, /* OBJ_pkcs8ShroudedKeyBag 1 2 840 113549 1 12 10 1 2 */
|
||||
152, /* OBJ_certBag 1 2 840 113549 1 12 10 1 3 */
|
||||
|
|
|
@ -1496,3 +1496,5 @@ aes_256_cbc_hmac_sha512_etm 1495
|
|||
HKDF_SHA256 1496
|
||||
HKDF_SHA384 1497
|
||||
HKDF_SHA512 1498
|
||||
id_smime_ori 1499
|
||||
id_smime_ori_kem 1500
|
||||
|
|
|
@ -251,6 +251,7 @@ SMIME 3 : id-smime-alg
|
|||
SMIME 4 : id-smime-cd
|
||||
SMIME 5 : id-smime-spq
|
||||
SMIME 6 : id-smime-cti
|
||||
SMIME 13 : id-smime-ori
|
||||
|
||||
# S/MIME Modules
|
||||
id-smime-mod 1 : id-smime-mod-cms
|
||||
|
@ -355,6 +356,9 @@ id-smime-cti 4 : id-smime-cti-ets-proofOfSender
|
|||
id-smime-cti 5 : id-smime-cti-ets-proofOfApproval
|
||||
id-smime-cti 6 : id-smime-cti-ets-proofOfCreation
|
||||
|
||||
# S/MIME OtherRecipientInfo Type Identifier
|
||||
id-smime-ori 3 : id-smime-ori-kem
|
||||
|
||||
pkcs9 20 : : friendlyName
|
||||
pkcs9 21 : : localKeyID
|
||||
!Alias ms-corp 1 3 6 1 4 1 311
|
||||
|
|
|
@ -0,0 +1,254 @@
|
|||
/*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#include "internal/common.h"
|
||||
#include "internal/threads_lock_contention.h"
|
||||
|
||||
#if defined(OPENSSL_THREADS) && !defined(CRYPTO_TDEBUG) && \
|
||||
!defined(OPENSSL_SYS_WINDOWS) && defined(REPORT_RWLOCK_CONTENTION)
|
||||
|
||||
# define _GNU_SOURCE
|
||||
|
||||
# include <assert.h>
|
||||
# include <execinfo.h>
|
||||
# include <fcntl.h>
|
||||
# include <stdbool.h>
|
||||
# include <unistd.h>
|
||||
# include <sys/syscall.h>
|
||||
# include <sys/uio.h>
|
||||
|
||||
# include "internal/time.h"
|
||||
|
||||
# define BT_BUF_SIZE 1024
|
||||
|
||||
/*
|
||||
* Normally we would use a BIO here to do this, but we create locks during
|
||||
* library initialization, and creating a bio too early, creates a recursive set
|
||||
* of stack calls that leads us to call CRYPTO_thread_run_once while currently
|
||||
* executing the init routine for various run_once functions, which leads to
|
||||
* deadlock. Avoid that by just using a FILE pointer. Also note that we
|
||||
* directly use a pthread_mutex_t to protect access from multiple threads
|
||||
* to the contention log file. We do this because we want to avoid use
|
||||
* of the CRYPTO_THREAD api so as to prevent recursive blocking reports.
|
||||
*/
|
||||
static CRYPTO_ONCE init_contention_data_flag = CRYPTO_ONCE_STATIC_INIT;
|
||||
pthread_mutex_t log_lock = PTHREAD_MUTEX_INITIALIZER;
|
||||
CRYPTO_THREAD_LOCAL thread_contention_data;
|
||||
|
||||
struct stack_info {
|
||||
unsigned int nptrs;
|
||||
int write;
|
||||
OSSL_TIME start;
|
||||
OSSL_TIME duration;
|
||||
char **strings;
|
||||
};
|
||||
|
||||
# define STACKS_COUNT 32
|
||||
struct stack_traces {
|
||||
int fd;
|
||||
int lock_depth;
|
||||
size_t idx;
|
||||
struct stack_info stacks[STACKS_COUNT];
|
||||
};
|
||||
|
||||
/* The glibc gettid() definition presents only since 2.30. */
|
||||
static pid_t get_tid()
|
||||
{
|
||||
return syscall(SYS_gettid);
|
||||
}
|
||||
|
||||
# ifdef FIPS_MODULE
|
||||
# define FIPS_SFX "-fips"
|
||||
# else
|
||||
# define FIPS_SFX ""
|
||||
# endif
|
||||
static void *init_contention_data(void)
|
||||
{
|
||||
struct stack_traces *traces;
|
||||
char fname_fmt[] = "lock-contention-log" FIPS_SFX ".%d.txt";
|
||||
char fname[sizeof(fname_fmt) + sizeof(int) * 3];
|
||||
|
||||
traces = OPENSSL_zalloc(sizeof(struct stack_traces));
|
||||
|
||||
snprintf(fname, sizeof(fname), fname_fmt, get_tid());
|
||||
|
||||
traces->fd = open(fname, O_WRONLY | O_APPEND | O_CLOEXEC | O_CREAT, 0600);
|
||||
|
||||
return traces;
|
||||
}
|
||||
|
||||
static void destroy_contention_data(void *data)
|
||||
{
|
||||
struct stack_traces *st = data;
|
||||
|
||||
close(st->fd);
|
||||
OPENSSL_free(data);
|
||||
}
|
||||
|
||||
static void init_contention_data_once(void)
|
||||
{
|
||||
/*
|
||||
* Create a thread local key here to store our list of stack traces
|
||||
* to be printed when we unlock the lock we are holding
|
||||
*/
|
||||
CRYPTO_THREAD_init_local(&thread_contention_data, destroy_contention_data);
|
||||
return;
|
||||
}
|
||||
|
||||
static struct stack_traces *get_stack_traces(bool init)
|
||||
{
|
||||
struct stack_traces *traces = CRYPTO_THREAD_get_local(&thread_contention_data);
|
||||
|
||||
if (!traces && init) {
|
||||
traces = init_contention_data();
|
||||
CRYPTO_THREAD_set_local(&thread_contention_data, traces);
|
||||
}
|
||||
|
||||
return traces;
|
||||
}
|
||||
|
||||
static void print_stack_traces(struct stack_traces *traces)
|
||||
{
|
||||
unsigned int j;
|
||||
struct iovec *iov;
|
||||
int iovcnt;
|
||||
|
||||
while (traces != NULL && traces->idx >= 1) {
|
||||
traces->idx--;
|
||||
dprintf(traces->fd,
|
||||
"lock blocked on %s for %zu usec at time %zu tid %d\n",
|
||||
traces->stacks[traces->idx].write == 1 ? "WRITE" : "READ",
|
||||
ossl_time2us(traces->stacks[traces->idx].duration),
|
||||
ossl_time2us(traces->stacks[traces->idx].start),
|
||||
get_tid());
|
||||
if (traces->stacks[traces->idx].strings != NULL) {
|
||||
static const char lf = '\n';
|
||||
|
||||
iovcnt = traces->stacks[traces->idx].nptrs * 2 + 1;
|
||||
iov = alloca(iovcnt * sizeof(*iov));
|
||||
for (j = 0; j < traces->stacks[traces->idx].nptrs; j++) {
|
||||
iov[2 * j].iov_base = traces->stacks[traces->idx].strings[j];
|
||||
iov[2 * j].iov_len = strlen(traces->stacks[traces->idx].strings[j]);
|
||||
iov[2 * j + 1].iov_base = (char *) &lf;
|
||||
iov[2 * j + 1].iov_len = 1;
|
||||
}
|
||||
iov[traces->stacks[traces->idx].nptrs * 2].iov_base = (char *) &lf;
|
||||
iov[traces->stacks[traces->idx].nptrs * 2].iov_len = 1;
|
||||
} else {
|
||||
static const char no_bt[] = "No stack trace available\n\n";
|
||||
|
||||
iovcnt = 1;
|
||||
iov = alloca(iovcnt * sizeof(*iov));
|
||||
iov[0].iov_base = (char *) no_bt;
|
||||
iov[0].iov_len = sizeof(no_bt) - 1;
|
||||
}
|
||||
writev(traces->fd, iov, iovcnt);
|
||||
free(traces->stacks[traces->idx].strings);
|
||||
}
|
||||
}
|
||||
|
||||
void ossl_init_rwlock_contention_data(void)
|
||||
{
|
||||
CRYPTO_THREAD_run_once(&init_contention_data_flag, init_contention_data_once);
|
||||
}
|
||||
|
||||
void ossl_free_rwlock_contention_data(void)
|
||||
{
|
||||
}
|
||||
|
||||
static int record_lock_contention(pthread_rwlock_t *lock,
|
||||
struct stack_traces *traces, bool write)
|
||||
{
|
||||
void *buffer[BT_BUF_SIZE];
|
||||
OSSL_TIME start, end;
|
||||
int ret;
|
||||
|
||||
start = ossl_time_now();
|
||||
ret = (write ? pthread_rwlock_wrlock : pthread_rwlock_rdlock)(lock);
|
||||
if (ret)
|
||||
return ret;
|
||||
end = ossl_time_now();
|
||||
traces->stacks[traces->idx].nptrs = backtrace(buffer, BT_BUF_SIZE);
|
||||
traces->stacks[traces->idx].strings = backtrace_symbols(buffer,
|
||||
traces->stacks[traces->idx].nptrs);
|
||||
traces->stacks[traces->idx].duration = ossl_time_subtract(end, start);
|
||||
traces->stacks[traces->idx].start = start;
|
||||
traces->stacks[traces->idx].write = write;
|
||||
traces->idx++;
|
||||
if (traces->idx >= STACKS_COUNT) {
|
||||
fprintf(stderr, "STACK RECORD OVERFLOW!\n");
|
||||
print_stack_traces(traces);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ossl_rwlock_rdlock(pthread_rwlock_t *lock)
|
||||
{
|
||||
struct stack_traces *traces = get_stack_traces(true);
|
||||
|
||||
if (ossl_unlikely(traces == NULL))
|
||||
return 1;
|
||||
|
||||
traces->lock_depth++;
|
||||
if (pthread_rwlock_tryrdlock(lock)) {
|
||||
int ret = record_lock_contention(lock, traces, false);
|
||||
|
||||
if (ret)
|
||||
traces->lock_depth--;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ossl_rwlock_wrlock(pthread_rwlock_t *lock)
|
||||
{
|
||||
struct stack_traces *traces = get_stack_traces(true);
|
||||
|
||||
if (ossl_unlikely(traces == NULL))
|
||||
return 1;
|
||||
|
||||
traces->lock_depth++;
|
||||
if (pthread_rwlock_trywrlock(lock)) {
|
||||
int ret = record_lock_contention(lock, traces, true);
|
||||
|
||||
if (ret)
|
||||
traces->lock_depth--;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ossl_rwlock_unlock(pthread_rwlock_t *lock)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = pthread_rwlock_unlock(lock);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
{
|
||||
struct stack_traces *traces = get_stack_traces(false);
|
||||
|
||||
if (traces != NULL) {
|
||||
traces->lock_depth--;
|
||||
assert(traces->lock_depth >= 0);
|
||||
if (traces->lock_depth == 0)
|
||||
print_stack_traces(traces);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* OPENSSL_THREADS && !CRYPTO_TDEBUG && !OPENSSL_SYS_WINDOWS && REPORT_RWLOCK_CONTENTION */
|
|
@ -10,36 +10,13 @@
|
|||
/* We need to use the OPENSSL_fork_*() deprecated APIs */
|
||||
#define OPENSSL_SUPPRESS_DEPRECATED
|
||||
|
||||
#if !defined(__GNUC__) || !defined(__ATOMIC_ACQ_REL) || \
|
||||
defined(BROKEN_CLANG_ATOMICS) || defined(OPENSSL_NO_STDIO)
|
||||
/*
|
||||
* we only enable REPORT_RWLOCK_CONTENTION on clang/gcc when we have
|
||||
* atomics available. We do this because we need to use an atomic to track
|
||||
* when we can close the log file. We could use the CRYPTO_atomic_ api
|
||||
* but that requires lock creation which gets us into a bad recursive loop
|
||||
* when we try to initialize the file pointer
|
||||
*/
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
# warning "RWLOCK CONTENTION REPORTING NOT SUPPORTED, Disabling"
|
||||
# undef REPORT_RWLOCK_CONTENTION
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef REPORT_RWLOCK_CONTENTION
|
||||
# define _GNU_SOURCE
|
||||
# include <execinfo.h>
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
#include <openssl/crypto.h>
|
||||
#include <crypto/cryptlib.h>
|
||||
#include <crypto/sparse_array.h>
|
||||
#include "internal/cryptlib.h"
|
||||
#include "internal/threads_common.h"
|
||||
#include "internal/threads_lock_contention.h"
|
||||
#include "internal/rcu.h"
|
||||
#ifdef REPORT_RWLOCK_CONTENTION
|
||||
# include "internal/time.h"
|
||||
#endif
|
||||
#include "rcu_internal.h"
|
||||
|
||||
#if defined(__clang__) && defined(__has_feature)
|
||||
|
@ -64,18 +41,6 @@ __tsan_mutex_post_lock((x), 0, 0)
|
|||
# include <atomic.h>
|
||||
#endif
|
||||
|
||||
#if defined(__apple_build_version__) && __apple_build_version__ < 6000000
|
||||
/*
|
||||
* OS/X 10.7 and 10.8 had a weird version of clang which has __ATOMIC_ACQUIRE and
|
||||
* __ATOMIC_ACQ_REL but which expects only one parameter for __atomic_is_lock_free()
|
||||
* rather than two which has signature __atomic_is_lock_free(sizeof(_Atomic(T))).
|
||||
* All of this makes impossible to use __atomic_is_lock_free here.
|
||||
*
|
||||
* See: https://github.com/llvm/llvm-project/commit/a4c2602b714e6c6edb98164550a5ae829b2de760
|
||||
*/
|
||||
# define BROKEN_CLANG_ATOMICS
|
||||
#endif
|
||||
|
||||
#if defined(OPENSSL_THREADS) && !defined(CRYPTO_TDEBUG) && !defined(OPENSSL_SYS_WINDOWS)
|
||||
|
||||
# if defined(OPENSSL_SYS_UNIX)
|
||||
|
@ -599,80 +564,12 @@ void ossl_rcu_lock_free(CRYPTO_RCU_LOCK *lock)
|
|||
OPENSSL_free(rlock);
|
||||
}
|
||||
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
/*
|
||||
* Normally we would use a BIO here to do this, but we create locks during
|
||||
* library initialization, and creating a bio too early, creates a recursive set
|
||||
* of stack calls that leads us to call CRYPTO_thread_run_once while currently
|
||||
* executing the init routine for various run_once functions, which leads to
|
||||
* deadlock. Avoid that by just using a FILE pointer. Also note that we
|
||||
* directly use a pthread_mutex_t to protect access from multiple threads
|
||||
* to the contention log file. We do this because we want to avoid use
|
||||
* of the CRYPTO_THREAD api so as to prevent recursive blocking reports.
|
||||
*/
|
||||
static FILE *contention_fp = NULL;
|
||||
static CRYPTO_ONCE init_contention_fp = CRYPTO_ONCE_STATIC_INIT;
|
||||
static int rwlock_count = 0;
|
||||
pthread_mutex_t log_lock = PTHREAD_MUTEX_INITIALIZER;
|
||||
CRYPTO_THREAD_LOCAL thread_contention_data;
|
||||
|
||||
static void destroy_contention_data(void *data)
|
||||
{
|
||||
OPENSSL_free(data);
|
||||
}
|
||||
|
||||
struct stack_info {
|
||||
unsigned int nptrs;
|
||||
int write;
|
||||
OSSL_TIME start;
|
||||
OSSL_TIME duration;
|
||||
char **strings;
|
||||
};
|
||||
|
||||
# define STACKS_COUNT 32
|
||||
struct stack_traces {
|
||||
int lock_depth;
|
||||
size_t idx;
|
||||
struct stack_info stacks[STACKS_COUNT];
|
||||
};
|
||||
|
||||
static void init_contention_fp_once(void)
|
||||
{
|
||||
# ifdef FIPS_MODULE
|
||||
contention_fp = fopen("lock-contention-log-fips.txt", "w");
|
||||
# else
|
||||
contention_fp = fopen("lock-contention-log.txt", "w");
|
||||
# endif
|
||||
if (contention_fp == NULL)
|
||||
fprintf(stderr, "Contention log file could not be opened, log will not be recorded\n");
|
||||
|
||||
/*
|
||||
* Create a thread local key here to store our list of stack traces
|
||||
* to be printed when we unlock the lock we are holding
|
||||
*/
|
||||
CRYPTO_THREAD_init_local(&thread_contention_data, destroy_contention_data);
|
||||
return;
|
||||
}
|
||||
# endif
|
||||
|
||||
CRYPTO_RWLOCK *CRYPTO_THREAD_lock_new(void)
|
||||
{
|
||||
# ifdef USE_RWLOCK
|
||||
CRYPTO_RWLOCK *lock;
|
||||
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
CRYPTO_THREAD_run_once(&init_contention_fp, init_contention_fp_once);
|
||||
__atomic_add_fetch(&rwlock_count, 1, __ATOMIC_ACQ_REL);
|
||||
{
|
||||
struct stack_info *thread_stack_info;
|
||||
|
||||
thread_stack_info = CRYPTO_THREAD_get_local(&thread_contention_data);
|
||||
if (thread_stack_info == NULL) {
|
||||
thread_stack_info = OPENSSL_zalloc(sizeof(struct stack_traces));
|
||||
CRYPTO_THREAD_set_local(&thread_contention_data, thread_stack_info);
|
||||
}
|
||||
}
|
||||
# endif
|
||||
ossl_init_rwlock_contention_data();
|
||||
|
||||
if ((lock = OPENSSL_zalloc(sizeof(pthread_rwlock_t))) == NULL)
|
||||
/* Don't set error, to avoid recursion blowup. */
|
||||
|
@ -714,75 +611,11 @@ CRYPTO_RWLOCK *CRYPTO_THREAD_lock_new(void)
|
|||
return lock;
|
||||
}
|
||||
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
static void print_stack_traces(struct stack_traces *traces, FILE *fptr)
|
||||
{
|
||||
unsigned int j;
|
||||
|
||||
pthread_mutex_lock(&log_lock);
|
||||
while (traces != NULL && traces->idx >= 1) {
|
||||
traces->idx--;
|
||||
fprintf(fptr, "lock blocked on %s for %zu usec at time %zu tid %d\n",
|
||||
traces->stacks[traces->idx].write == 1 ? "WRITE" : "READ",
|
||||
ossl_time2us(traces->stacks[traces->idx].duration),
|
||||
ossl_time2us(traces->stacks[traces->idx].start),
|
||||
gettid());
|
||||
if (traces->stacks[traces->idx].strings != NULL) {
|
||||
for (j = 0; j < traces->stacks[traces->idx].nptrs; j++)
|
||||
fprintf(fptr, "%s\n", traces->stacks[traces->idx].strings[j]);
|
||||
free(traces->stacks[traces->idx].strings);
|
||||
} else {
|
||||
fprintf(fptr, "No stack trace available\n");
|
||||
}
|
||||
fprintf(contention_fp, "\n");
|
||||
}
|
||||
pthread_mutex_unlock(&log_lock);
|
||||
}
|
||||
# endif
|
||||
|
||||
# define BT_BUF_SIZE 1024
|
||||
|
||||
__owur int CRYPTO_THREAD_read_lock(CRYPTO_RWLOCK *lock)
|
||||
{
|
||||
# ifdef USE_RWLOCK
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
struct stack_traces *traces = CRYPTO_THREAD_get_local(&thread_contention_data);
|
||||
|
||||
if (ossl_unlikely(traces == NULL)) {
|
||||
traces = OPENSSL_zalloc(sizeof(struct stack_traces));
|
||||
CRYPTO_THREAD_set_local(&thread_contention_data, traces);
|
||||
if (ossl_unlikely(traces == NULL))
|
||||
if (!ossl_assert(ossl_rwlock_rdlock(lock) == 0))
|
||||
return 0;
|
||||
}
|
||||
|
||||
traces->lock_depth++;
|
||||
if (pthread_rwlock_tryrdlock(lock)) {
|
||||
void *buffer[BT_BUF_SIZE];
|
||||
OSSL_TIME start, end;
|
||||
|
||||
start = ossl_time_now();
|
||||
if (!ossl_assert(pthread_rwlock_rdlock(lock) == 0)) {
|
||||
traces->lock_depth--;
|
||||
return 0;
|
||||
}
|
||||
end = ossl_time_now();
|
||||
traces->stacks[traces->idx].duration = ossl_time_subtract(end, start);
|
||||
traces->stacks[traces->idx].nptrs = backtrace(buffer, BT_BUF_SIZE);
|
||||
traces->stacks[traces->idx].strings = backtrace_symbols(buffer,
|
||||
traces->stacks[traces->idx].nptrs);
|
||||
traces->stacks[traces->idx].duration = ossl_time_subtract(end, start);
|
||||
traces->stacks[traces->idx].start = start;
|
||||
traces->stacks[traces->idx].write = 0;
|
||||
traces->idx++;
|
||||
if (traces->idx >= STACKS_COUNT) {
|
||||
fprintf(stderr, "STACK RECORD OVERFLOW!\n");
|
||||
print_stack_traces(traces, contention_fp);
|
||||
}
|
||||
}
|
||||
# else
|
||||
if (!ossl_assert(pthread_rwlock_rdlock(lock) == 0))
|
||||
return 0;
|
||||
# endif
|
||||
# else
|
||||
if (pthread_mutex_lock(lock) != 0) {
|
||||
assert(errno != EDEADLK && errno != EBUSY);
|
||||
|
@ -796,43 +629,8 @@ __owur int CRYPTO_THREAD_read_lock(CRYPTO_RWLOCK *lock)
|
|||
__owur int CRYPTO_THREAD_write_lock(CRYPTO_RWLOCK *lock)
|
||||
{
|
||||
# ifdef USE_RWLOCK
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
struct stack_traces *traces = CRYPTO_THREAD_get_local(&thread_contention_data);
|
||||
|
||||
if (ossl_unlikely(traces == NULL)) {
|
||||
traces = OPENSSL_zalloc(sizeof(struct stack_traces));
|
||||
CRYPTO_THREAD_set_local(&thread_contention_data, traces);
|
||||
if (ossl_unlikely(traces == NULL))
|
||||
if (!ossl_assert(ossl_rwlock_wrlock(lock) == 0))
|
||||
return 0;
|
||||
}
|
||||
|
||||
traces->lock_depth++;
|
||||
if (pthread_rwlock_trywrlock(lock)) {
|
||||
void *buffer[BT_BUF_SIZE];
|
||||
OSSL_TIME start, end;
|
||||
|
||||
start = ossl_time_now();
|
||||
if (!ossl_assert(pthread_rwlock_wrlock(lock) == 0)) {
|
||||
traces->lock_depth--;
|
||||
return 0;
|
||||
}
|
||||
end = ossl_time_now();
|
||||
traces->stacks[traces->idx].nptrs = backtrace(buffer, BT_BUF_SIZE);
|
||||
traces->stacks[traces->idx].strings = backtrace_symbols(buffer,
|
||||
traces->stacks[traces->idx].nptrs);
|
||||
traces->stacks[traces->idx].duration = ossl_time_subtract(end, start);
|
||||
traces->stacks[traces->idx].start = start;
|
||||
traces->stacks[traces->idx].write = 1;
|
||||
traces->idx++;
|
||||
if (traces->idx >= STACKS_COUNT) {
|
||||
fprintf(stderr, "STACK RECORD OVERFLOW!\n");
|
||||
print_stack_traces(traces, contention_fp);
|
||||
}
|
||||
}
|
||||
# else
|
||||
if (!ossl_assert(pthread_rwlock_wrlock(lock) == 0))
|
||||
return 0;
|
||||
# endif
|
||||
# else
|
||||
if (pthread_mutex_lock(lock) != 0) {
|
||||
assert(errno != EDEADLK && errno != EBUSY);
|
||||
|
@ -846,20 +644,8 @@ __owur int CRYPTO_THREAD_write_lock(CRYPTO_RWLOCK *lock)
|
|||
int CRYPTO_THREAD_unlock(CRYPTO_RWLOCK *lock)
|
||||
{
|
||||
# ifdef USE_RWLOCK
|
||||
if (pthread_rwlock_unlock(lock) != 0)
|
||||
if (ossl_rwlock_unlock(lock) != 0)
|
||||
return 0;
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
{
|
||||
struct stack_traces *traces = CRYPTO_THREAD_get_local(&thread_contention_data);
|
||||
|
||||
if (contention_fp != NULL && traces != NULL) {
|
||||
traces->lock_depth--;
|
||||
assert(traces->lock_depth >= 0);
|
||||
if (traces->lock_depth == 0)
|
||||
print_stack_traces(traces, contention_fp);
|
||||
}
|
||||
}
|
||||
# endif
|
||||
# else
|
||||
if (pthread_mutex_unlock(lock) != 0) {
|
||||
assert(errno != EPERM);
|
||||
|
@ -874,22 +660,9 @@ void CRYPTO_THREAD_lock_free(CRYPTO_RWLOCK *lock)
|
|||
{
|
||||
if (lock == NULL)
|
||||
return;
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
|
||||
/*
|
||||
* Note: It's possible here that OpenSSL may allocate a lock and immediately
|
||||
* free it, in which case we would erroneously close the contention log
|
||||
* prior to the library going on to do more real work. In practice
|
||||
* that never happens though, and since this is a debug facility
|
||||
* we don't worry about that here.
|
||||
*/
|
||||
if (__atomic_add_fetch(&rwlock_count, -1, __ATOMIC_ACQ_REL) == 0) {
|
||||
fclose(contention_fp);
|
||||
contention_fp = NULL;
|
||||
}
|
||||
# endif
|
||||
|
||||
# ifdef USE_RWLOCK
|
||||
ossl_free_rwlock_contention_data();
|
||||
pthread_rwlock_destroy(lock);
|
||||
# else
|
||||
pthread_mutex_destroy(lock);
|
||||
|
|
|
@ -75,6 +75,8 @@ Encryption options:
|
|||
[B<-aes256-wrap>]
|
||||
[B<-des3-wrap>]
|
||||
[B<-debug_decrypt>]
|
||||
[B<-recip_kdf> I<kdf>]
|
||||
[B<-recip_ukm> I<ukm>]
|
||||
|
||||
Signing options:
|
||||
|
||||
|
@ -450,6 +452,19 @@ Depending on the OpenSSL build options used, B<-des3-wrap> may not be supported.
|
|||
This option sets the B<CMS_DEBUG_DECRYPT> flag. This option should be used
|
||||
with caution: see the notes section below.
|
||||
|
||||
=item B<-recip_kdf>
|
||||
|
||||
This option sets the KDF used to generate the key encryption key in the
|
||||
B<KEMRecipientInfo> type. Any KDF that takes B<OSSL_KDF_PARAM_KEY> and
|
||||
B<OSSL_KDF_PARAM_INFO> parameters and is otherwise fully defined by its name or
|
||||
OID can be used, for example B<HKDF-SHA256>.
|
||||
|
||||
=item B<-recip_ukm>
|
||||
|
||||
This option sets the B<KEMRecipientInfo> type's optional user keying material (UKM)
|
||||
in hexadecimal form. The UKM will be encoded, along with other information, into the
|
||||
B<OSSL_KDF_PARAM_INFO> parameter of the B<KEMRecipientInfo> type's KDF.
|
||||
|
||||
=back
|
||||
|
||||
=head2 Signing options
|
||||
|
@ -937,6 +952,8 @@ The B<-engine> option was deprecated in OpenSSL 3.0.
|
|||
|
||||
The B<-digest> option was added in OpenSSL 3.2.
|
||||
|
||||
The B<-recip_kdf> and B<-recip_ukm> options were added in OpenSSL 3.6.
|
||||
|
||||
=head1 COPYRIGHT
|
||||
|
||||
Copyright 2008-2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
|
|
|
@ -133,6 +133,13 @@ By default, this command only lists each directory as it is processed.
|
|||
The path to an executable to use to generate hashes and
|
||||
fingerprints (see above).
|
||||
|
||||
=item B<PATH>
|
||||
|
||||
List of paths, separated by colons (or semicolons, on Windows platforms),
|
||||
where the B<openssl> executable is searched in case the path to the hash
|
||||
generating executable is not provided in the B<OPENSSL> environment variable
|
||||
or it is not usable (that is, does not exist or is not executable).
|
||||
|
||||
=item B<SSL_CERT_DIR>
|
||||
|
||||
Colon separated list of directories to operate on.
|
||||
|
|
|
@ -134,6 +134,18 @@ See L<openssl(1)/TLS Version Options>.
|
|||
|
||||
=back
|
||||
|
||||
=head1 ENVIRONMENT
|
||||
|
||||
=over 4
|
||||
|
||||
=item B<SSL_CIPHER>
|
||||
|
||||
If the B<-cipher> option is not specified, the contents of this environment
|
||||
variable are used to modify the TLSv1.2 and below cipher list sent
|
||||
by the client the same way the aforementioned option does.
|
||||
|
||||
=back
|
||||
|
||||
=head1 NOTES
|
||||
|
||||
This command can be used to measure the performance of an SSL connection.
|
||||
|
|
|
@ -30,7 +30,8 @@ The originator-related fields are relevant only in case when the keyAgreement
|
|||
method of providing of the shared key is in use.
|
||||
|
||||
CMS_add1_recipient_cert() adds recipient B<recip> to CMS_ContentInfo enveloped
|
||||
data structure B<cms> as a KeyTransRecipientInfo structure.
|
||||
data structure B<cms> as a KeyTransRecipientInfo or KEMRecipientInfo structure,
|
||||
or as a KeyAgreeRecipientInfo structure with an ephemeral key.
|
||||
|
||||
CMS_add0_recipient_key() adds symmetric key B<key> of length B<keylen> using
|
||||
wrapping algorithm B<nid>, identifier B<id> of length B<idlen> and optional
|
||||
|
|
|
@ -78,10 +78,12 @@ BIO_new_CMS().
|
|||
|
||||
The recipients specified in B<certs> use a CMS KeyTransRecipientInfo info
|
||||
structure. KEKRecipientInfo is also supported using the flag B<CMS_PARTIAL>
|
||||
and CMS_add0_recipient_key().
|
||||
and CMS_add0_recipient_key(). KEMRecipientInfo is also supported using the
|
||||
flag B<CMS_PARTIAL> and CMS_add1_recipient().
|
||||
|
||||
The parameter B<certs> may be NULL if B<CMS_PARTIAL> is set and recipients
|
||||
added later using CMS_add1_recipient_cert() or CMS_add0_recipient_key().
|
||||
are added later using CMS_add1_recipient() or CMS_add1_recipient_cert() with
|
||||
CMS_add0_recipient_key().
|
||||
|
||||
CMS_encrypt() is similar to CMS_encrypt_ex() but uses default values
|
||||
of NULL for the library context I<libctx> and the property query I<propq>.
|
||||
|
@ -104,7 +106,7 @@ The B<CMS_STREAM> flag was first supported in OpenSSL 1.0.0.
|
|||
|
||||
=head1 COPYRIGHT
|
||||
|
||||
Copyright 2008-2020 The OpenSSL Project Authors. All Rights Reserved.
|
||||
Copyright 2008-2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
|
||||
Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
this file except in compliance with the License. You can obtain a copy
|
||||
|
|
|
@ -6,9 +6,12 @@ CMS_get0_RecipientInfos, CMS_RecipientInfo_type,
|
|||
CMS_RecipientInfo_ktri_get0_signer_id, CMS_RecipientInfo_ktri_cert_cmp,
|
||||
CMS_RecipientInfo_set0_pkey, CMS_RecipientInfo_kekri_get0_id,
|
||||
CMS_RecipientInfo_kari_set0_pkey_and_peer,
|
||||
CMS_RecipientInfo_kari_set0_pkey,
|
||||
CMS_RecipientInfo_kari_set0_pkey, CMS_RecipientInfo_kari_get0_ctx,
|
||||
CMS_RecipientInfo_kekri_id_cmp, CMS_RecipientInfo_set0_key,
|
||||
CMS_RecipientInfo_decrypt, CMS_RecipientInfo_encrypt
|
||||
CMS_RecipientInfo_kemri_cert_cmp, CMS_RecipientInfo_kemri_set0_pkey,
|
||||
CMS_RecipientInfo_kemri_get0_ctx, CMS_RecipientInfo_kemri_get0_kdf_alg,
|
||||
CMS_RecipientInfo_kemri_set_ukm, CMS_RecipientInfo_decrypt,
|
||||
CMS_RecipientInfo_encrypt
|
||||
- CMS envelopedData RecipientInfo routines
|
||||
|
||||
=head1 SYNOPSIS
|
||||
|
@ -27,6 +30,7 @@ CMS_RecipientInfo_decrypt, CMS_RecipientInfo_encrypt
|
|||
int CMS_RecipientInfo_kari_set0_pkey_and_peer(CMS_RecipientInfo *ri,
|
||||
EVP_PKEY *pk, X509 *peer);
|
||||
int CMS_RecipientInfo_kari_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pk);
|
||||
EVP_CIPHER_CTX *CMS_RecipientInfo_kari_get0_ctx(CMS_RecipientInfo *ri);
|
||||
int CMS_RecipientInfo_kekri_get0_id(CMS_RecipientInfo *ri, X509_ALGOR **palg,
|
||||
ASN1_OCTET_STRING **pid,
|
||||
ASN1_GENERALIZEDTIME **pdate,
|
||||
|
@ -36,6 +40,13 @@ CMS_RecipientInfo_decrypt, CMS_RecipientInfo_encrypt
|
|||
const unsigned char *id, size_t idlen);
|
||||
int CMS_RecipientInfo_set0_key(CMS_RecipientInfo *ri,
|
||||
unsigned char *key, size_t keylen);
|
||||
int CMS_RecipientInfo_kemri_cert_cmp(CMS_RecipientInfo *ri, X509 *cert);
|
||||
int CMS_RecipientInfo_kemri_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pk);
|
||||
EVP_CIPHER_CTX *CMS_RecipientInfo_kemri_get0_ctx(CMS_RecipientInfo *ri);
|
||||
X509_ALGOR *CMS_RecipientInfo_kemri_get0_kdf_alg(CMS_RecipientInfo *ri);
|
||||
int CMS_RecipientInfo_kemri_set_ukm(CMS_RecipientInfo *ri,
|
||||
const unsigned char *ukm,
|
||||
int ukmLength);
|
||||
|
||||
int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
|
||||
int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri);
|
||||
|
@ -47,7 +58,8 @@ structures associated with a CMS EnvelopedData structure.
|
|||
|
||||
CMS_RecipientInfo_type() returns the type of CMS_RecipientInfo structure B<ri>.
|
||||
It will currently return CMS_RECIPINFO_TRANS, CMS_RECIPINFO_AGREE,
|
||||
CMS_RECIPINFO_KEK, CMS_RECIPINFO_PASS, or CMS_RECIPINFO_OTHER.
|
||||
CMS_RECIPINFO_KEK, CMS_RECIPINFO_PASS, CMS_RECIPINFO_KEM, or
|
||||
CMS_RECIPINFO_OTHER.
|
||||
|
||||
CMS_RecipientInfo_ktri_get0_signer_id() retrieves the certificate recipient
|
||||
identifier associated with a specific CMS_RecipientInfo structure B<ri>, which
|
||||
|
@ -69,6 +81,10 @@ must be of type CMS_RECIPINFO_AGREE.
|
|||
CMS_RecipientInfo_kari_set0_pkey() associates the private key B<pkey> with the
|
||||
CMS_RecipientInfo structure B<ri>, which must be of type CMS_RECIPINFO_AGREE.
|
||||
|
||||
CMS_RecipientInfo_kari_get0_ctx() returns the EVP_CIPHER_CTX for the key
|
||||
encryption key, allowing the caller to specify the key wrap cipher. The
|
||||
CMS_RecipientInfo structure B<ri> must be of type CMS_RECIPINFO_AGREE.
|
||||
|
||||
CMS_RecipientInfo_kekri_get0_id() retrieves the key information from the
|
||||
CMS_RecipientInfo structure B<ri> which must be of type CMS_RECIPINFO_KEK. Any
|
||||
of the remaining parameters can be NULL if the application is not interested in
|
||||
|
@ -88,6 +104,27 @@ CMS_RecipientInfo_set0_key() associates the symmetric key B<key> of length
|
|||
B<keylen> with the CMS_RecipientInfo structure B<ri>, which must be of type
|
||||
CMS_RECIPINFO_KEK.
|
||||
|
||||
CMS_RecipientInfo_kemri_cert_cmp() compares the certificate B<cert> against the
|
||||
CMS_RecipientInfo structure B<ri>, which must be of type CMS_RECIPINFO_KEM.
|
||||
It returns zero if the comparison is successful and non zero if not.
|
||||
|
||||
CMS_RecipientInfo_kemri_set0_pkey() associates the private key B<pkey> with the
|
||||
CMS_RecipientInfo structure B<ri>, which must be of type CMS_RECIPINFO_KEM.
|
||||
|
||||
CMS_RecipientInfo_kemri_get0_ctx() returns the EVP_CIPHER_CTX for the key
|
||||
encryption key, allowing the caller to specify the key wrap cipher. The
|
||||
CMS_RecipientInfo structure B<ri> must be of type CMS_RECIPINFO_KEM.
|
||||
|
||||
CMS_RecipientInfo_kemri_get0_kdf_alg() returns the X509_ALGOR for the
|
||||
RecipientInfo's KDF, allowing the caller to specify the KDF algorithm. The
|
||||
CMS_RecipientInfo structure B<ri> must be of type CMS_RECIPINFO_KEM. If the
|
||||
caller doesn't specify a KDF algorithm, B<HKDF-SHA256> will be used.
|
||||
|
||||
CMS_RecipientInfo_kemri_set_ukm() sets the RecipientInfo's optional user
|
||||
keying material (UKM). The UKM is encoded, along with other information, into
|
||||
the B<OSSL_KDF_PARAM_INFO> parameter of the RecipientInfo's KDF. The
|
||||
CMS_RecipientInfo structure B<ri> must be of type CMS_RECIPINFO_KEM.
|
||||
|
||||
CMS_RecipientInfo_decrypt() attempts to decrypt CMS_RecipientInfo structure
|
||||
B<ri> in structure B<cms>. A key must have been associated with the structure
|
||||
first.
|
||||
|
@ -125,12 +162,20 @@ CMS_get0_RecipientInfos() returns all CMS_RecipientInfo structures, or NULL if
|
|||
an error occurs.
|
||||
|
||||
CMS_RecipientInfo_ktri_get0_signer_id(), CMS_RecipientInfo_set0_pkey(),
|
||||
CMS_RecipientInfo_kekri_get0_id(), CMS_RecipientInfo_set0_key() and
|
||||
CMS_RecipientInfo_decrypt() return 1 for success or 0 if an error occurs.
|
||||
CMS_RecipientInfo_encrypt() return 1 for success or 0 if an error occurs.
|
||||
CMS_RecipientInfo_kekri_get0_id(), CMS_RecipientInfo_set0_key(),
|
||||
CMS_RecipientInfo_kemri_set0_pkey(), CMS_RecipientInfo_kemri_set_ukm(),
|
||||
CMS_RecipientInfo_decrypt() and CMS_RecipientInfo_encrypt() return 1 for
|
||||
success or 0 if an error occurs.
|
||||
|
||||
CMS_RecipientInfo_ktri_cert_cmp() and CMS_RecipientInfo_kekri_cmp() return 0
|
||||
for a successful comparison and non zero otherwise.
|
||||
CMS_RecipientInfo_ktri_cert_cmp(), CMS_RecipientInfo_kemri_cert_cmp() and
|
||||
CMS_RecipientInfo_kekri_cmp() return 0 for a successful comparison and non zero
|
||||
otherwise.
|
||||
|
||||
CMS_RecipientInfo_kemri_get0_ctx() and CMS_RecipientInfo_kari_get0_ctx return
|
||||
the RecipientInfo's EVP_CIPHER_CTX or NULL if an error occurred.
|
||||
|
||||
CMS_RecipientInfo_kemri_get0_kdf_alg() returns the RecipientInfo's KDF's
|
||||
X509_ALGOR or NULL if an error occurred.
|
||||
|
||||
Any error can be obtained from L<ERR_get_error(3)>.
|
||||
|
||||
|
@ -143,9 +188,13 @@ L<ERR_get_error(3)>, L<CMS_decrypt(3)>
|
|||
B<CMS_RecipientInfo_kari_set0_pkey_and_peer> and B<CMS_RecipientInfo_kari_set0_pkey>
|
||||
were added in OpenSSL 3.0.
|
||||
|
||||
B<CMS_RecipientInfo_kemri_cert_cmp>, B<CMS_RecipientInfo_kemri_set0_pkey>,
|
||||
B<CMS_RecipientInfo_kemri_get0_ctx>, B<CMS_RecipientInfo_kemri_get0_kdf_alg>
|
||||
and B<CMS_RecipientInfo_kemri_set_ukm> were added in OpenSSL 3.6.
|
||||
|
||||
=head1 COPYRIGHT
|
||||
|
||||
Copyright 2008-2020 The OpenSSL Project Authors. All Rights Reserved.
|
||||
Copyright 2008-2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
|
||||
Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
this file except in compliance with the License. You can obtain a copy
|
||||
|
|
|
@ -18,7 +18,8 @@ CRYPTO_get_alloc_counts,
|
|||
CRYPTO_set_mem_debug, CRYPTO_mem_ctrl,
|
||||
CRYPTO_mem_leaks, CRYPTO_mem_leaks_fp, CRYPTO_mem_leaks_cb,
|
||||
OPENSSL_MALLOC_FAILURES,
|
||||
OPENSSL_MALLOC_FD
|
||||
OPENSSL_MALLOC_FD,
|
||||
OPENSSL_MALLOC_SEED
|
||||
- Memory allocation functions
|
||||
|
||||
=head1 SYNOPSIS
|
||||
|
@ -69,6 +70,7 @@ OPENSSL_MALLOC_FD
|
|||
|
||||
env OPENSSL_MALLOC_FAILURES=... <application>
|
||||
env OPENSSL_MALLOC_FD=... <application>
|
||||
env OPENSSL_MALLOC_SEED=... <application>
|
||||
|
||||
The following functions have been deprecated since OpenSSL 3.0, and can be
|
||||
hidden entirely by defining B<OPENSSL_API_COMPAT> with a suitable version value,
|
||||
|
@ -155,9 +157,9 @@ with CRYPTO_set_mem_functions(), it's recommended to swap them all out
|
|||
at once.
|
||||
|
||||
If the library is built with the C<crypto-mdebug> option, then one
|
||||
function, CRYPTO_get_alloc_counts(), and two additional environment
|
||||
variables, B<OPENSSL_MALLOC_FAILURES> and B<OPENSSL_MALLOC_FD>,
|
||||
are available.
|
||||
function, CRYPTO_get_alloc_counts(), and three additional environment
|
||||
variables, B<OPENSSL_MALLOC_FAILURES>, B<OPENSSL_MALLOC_FD>,
|
||||
and B<OPENSSL_MALLOC_SEED>, are available.
|
||||
|
||||
The function CRYPTO_get_alloc_counts() fills in the number of times
|
||||
each of CRYPTO_malloc(), CRYPTO_realloc(), and CRYPTO_free() have been
|
||||
|
@ -167,12 +169,14 @@ respectively. If a pointer is NULL, then the corresponding count is not stored.
|
|||
The variable
|
||||
B<OPENSSL_MALLOC_FAILURES> controls how often allocations should fail.
|
||||
It is a set of fields separated by semicolons, which each field is a count
|
||||
(defaulting to zero) and an optional atsign and percentage (defaulting
|
||||
to 100). If the count is zero, then it lasts forever. For example,
|
||||
C<100;@25> or C<100@0;0@25> means the first 100 allocations pass, then all
|
||||
other allocations (until the program exits or crashes) have a 25% chance of
|
||||
failing. The length of the value of B<OPENSSL_MALLOC_FAILURES> must be 256 or
|
||||
fewer characters.
|
||||
(defaulting to zero) and an optional atsign and percentage (interpreted
|
||||
as a floating point number that is rounded up to two decimal digits
|
||||
of precision, defaulting to 100). If the count is zero, then it lasts forever.
|
||||
For example, C<100;@0.258> or C<100@0;0@0.258> means the first 100 allocations
|
||||
pass, then all other allocations (until the program exits or crashes) have
|
||||
a 0.26% chance of failing, with random(3) used as a source of randomness.
|
||||
The length of the value of B<OPENSSL_MALLOC_FAILURES> must be 256 or fewer
|
||||
characters.
|
||||
|
||||
If the variable B<OPENSSL_MALLOC_FD> is parsed as a positive integer, then
|
||||
it is taken as an open file descriptor. This is used in conjunction with
|
||||
|
@ -188,6 +192,10 @@ work on all platforms):
|
|||
export OPENSSL_MALLOC_FD
|
||||
...app invocation... 3>/tmp/log$$
|
||||
|
||||
If the environment variable B<OPENSSL_MALLOC_SEED> is set, its value
|
||||
is interpreted as an integer using atoi(3) and supplied to the srandom(3)
|
||||
call for the random number generator initialisation.
|
||||
|
||||
=head1 RETURN VALUES
|
||||
|
||||
OPENSSL_malloc_init(), OPENSSL_free(), OPENSSL_clear_free()
|
||||
|
|
|
@ -67,6 +67,28 @@ given passphrase. See L<passphrase-encoding(7)> for more information.
|
|||
|
||||
All functions returning an integer return 1 on success and 0 if an error occurred.
|
||||
|
||||
=head1 ENVIRONMENT
|
||||
|
||||
=over 4
|
||||
|
||||
=item B<LEGACY_GOST_PKCS12>
|
||||
|
||||
=for comment
|
||||
https://tc26.ru/standarts/metodicheskie-rekomendatsii/transportnyy-klyuchevoy-konteyner.html section 5.1
|
||||
https://tc26.ru/standard/rs/%D0%A0%2050.1.112-2016.pdf section 5
|
||||
https://meganorm.ru/mega_doc/norm/prikaz/25/r_1323565_1_041-2022_rekomendatsii_po_standartizatsii.html section 7.1
|
||||
|
||||
If this environment variable is set, MAC generation that utilises
|
||||
GOST R 34.11-94 or GOST 34.11-2012 hashing algorithms is performed the usual
|
||||
way and not in accordance with the specification provided in the methodical
|
||||
recommendation MP 26.2.002-2012 (or in its later versions, standartisation
|
||||
recommendation P 50.1.112-2016 or P 1323565.1.041-2022)
|
||||
of Technical Committee 26, that specifies that the key used for MAC
|
||||
generation should be the last 32 bytes of the 96-byte sequence generated
|
||||
by L<PKCS5_PBKDF2_HMAC(3)> and not the whole sequence.
|
||||
|
||||
=back
|
||||
|
||||
=head1 CONFORMING TO
|
||||
|
||||
IETF RFC 7292 (L<https://tools.ietf.org/html/rfc7292>)
|
||||
|
|
|
@ -6,10 +6,11 @@ openssl-env - OpenSSL environment variables
|
|||
|
||||
=head1 DESCRIPTION
|
||||
|
||||
The OpenSSL libraries use environment variables to override the
|
||||
compiled-in default paths for various data.
|
||||
To avoid security risks, the environment is usually not consulted when
|
||||
the executable is set-user-ID or set-group-ID.
|
||||
The OpenSSL libraries and commands use environment variables to override
|
||||
compiled-in defaults for various aspects of their behaviour.
|
||||
To avoid security risks, the environment is not consulted
|
||||
for security-sensitive environment variables when the executable
|
||||
is set-user-ID or set-group-ID.
|
||||
|
||||
=over 4
|
||||
|
||||
|
@ -18,39 +19,85 @@ the executable is set-user-ID or set-group-ID.
|
|||
Specifies the path to a certificate transparency log list.
|
||||
See L<CTLOG_STORE_new(3)>.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<HOME>, B<SYSTEMROOT>, B<USERPROFILE>
|
||||
|
||||
Path which L<RAND_file_name(3)> uses as a directory for the random seed file
|
||||
name when the B<RANDFILE> environment variable is not set.
|
||||
B<HOME> is the only variable that is considered on Unix-like systems;
|
||||
B<USERPROFILE> and B<SYSTEMROOT> are used as fallbacks on Windows platforms.
|
||||
|
||||
B<HOME> variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<HTTPS_PROXY>, B<HTTP_PROXY>, B<NO_PROXY>, B<https_proxy>, B<http_proxy>, B<no_proxy>
|
||||
|
||||
Specify a proxy hostname.
|
||||
See L<OSSL_HTTP_parse_url(3)>.
|
||||
|
||||
These variables are considered security-sensitive environment variables.
|
||||
|
||||
=item B<LEGACY_GOST_PKCS12>
|
||||
|
||||
Affects the way MAC is generated in PKCS#12 containers for GOST algorithms.
|
||||
See L<PKCS12_gen_mac(3)>.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<OPENSSL>
|
||||
|
||||
Specifies the path to the B<openssl> executable. Used by
|
||||
the B<rehash> script (see L<openssl-rehash(1)/Script Configuration>)
|
||||
and by the B<CA.pl> script (see L<CA.pl(1)/NOTES>
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_CONF>, B<OPENSSL_CONF_INCLUDE>
|
||||
|
||||
Specifies the path to a configuration file and the directory for
|
||||
included files.
|
||||
See L<config(5)>.
|
||||
|
||||
These variables are considered security-sensitive environment variables.
|
||||
|
||||
=item B<OPENSSL_CONFIG>
|
||||
|
||||
Specifies a configuration option and filename for the B<req> and B<ca>
|
||||
commands invoked by the B<CA.pl> script.
|
||||
See L<CA.pl(1)>.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_DEBUG_DECC_INIT>
|
||||
|
||||
On VMS only: if this variable is set, enables verbose output of parsing
|
||||
of C<DECC$*> logical names, that contain C RTL features, during library
|
||||
initialisation (C<LIB$INITIALIZE>). If the value of the variable is more
|
||||
than 1, outputs information about every processed feature.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_ENGINES>
|
||||
|
||||
Specifies the directory from which dynamic engines are loaded.
|
||||
See L<openssl-engine(1)>.
|
||||
|
||||
=item B<OPENSSL_MALLOC_FD>, B<OPENSSL_MALLOC_FAILURES>
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<OPENSSL_MALLOC_FAILURES>, B<OPENSSL_MALLOC_FD>, B<OPENSSL_MALLOC_SEED>
|
||||
|
||||
If built with debugging, this allows memory allocation to fail.
|
||||
See L<OPENSSL_malloc(3)>.
|
||||
|
||||
These variables are not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_MODULES>
|
||||
|
||||
Specifies the directory from which cryptographic providers are loaded.
|
||||
Equivalently, the generic B<-provider-path> command-line option may be used.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<OPENSSL_SEC_MEM>
|
||||
|
||||
Initializes the secure memory at the beginning of the application which makes
|
||||
|
@ -59,12 +106,24 @@ indicates the B<size> parameter in bytes. The value can be expressed in
|
|||
binary, octal, decimal and hexadecimal. For formatting see B<strtol(3)>.
|
||||
For further restrictions see L<CRYPTO_secure_malloc_init(3)>.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_SEC_MEM_MINSIZE>
|
||||
|
||||
An optional variable used with B<OPENSSL_SEC_MEM>. The value indicates
|
||||
B<minsize> parameter in bytes. The same formatting applies as above.
|
||||
Default is 0. For more info see L<CRYPTO_secure_malloc_init(3)>.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_TEST_LIBCTX>
|
||||
|
||||
This test-only environment variable, that is recognised by the L<openssl(1)>
|
||||
command, when is set to "1", leads to creation of a nondefault library context
|
||||
by the command, for which the B<-config> option then takes effect.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_TRACE>
|
||||
|
||||
By default the OpenSSL trace feature is disabled statically.
|
||||
|
@ -75,58 +134,14 @@ Unless OpenSSL tracing support is generally disabled,
|
|||
enable trace output of specific parts of OpenSSL libraries, by name.
|
||||
This output usually makes sense only if you know OpenSSL internals well.
|
||||
|
||||
The value of this environment varialble is a comma-separated list of names,
|
||||
The value of this environment variable is a comma-separated list of names,
|
||||
with the following available:
|
||||
|
||||
=over 4
|
||||
|
||||
=item B<TRACE>
|
||||
=item B<ALL>
|
||||
|
||||
Traces the OpenSSL trace API itself.
|
||||
|
||||
=item B<INIT>
|
||||
|
||||
Traces OpenSSL library initialization and cleanup.
|
||||
|
||||
=item B<TLS>
|
||||
|
||||
Traces the TLS/SSL protocol.
|
||||
|
||||
=item B<TLS_CIPHER>
|
||||
|
||||
Traces the ciphers used by the TLS/SSL protocol.
|
||||
|
||||
=item B<CONF>
|
||||
|
||||
Show details about provider and engine configuration.
|
||||
|
||||
=item B<ENGINE_TABLE>
|
||||
|
||||
The function that is used by RSA, DSA (etc) code to select registered
|
||||
ENGINEs, cache defaults and functional references (etc), will generate
|
||||
debugging summaries.
|
||||
|
||||
=item B<ENGINE_REF_COUNT>
|
||||
|
||||
Reference counts in the ENGINE structure will be monitored with a line
|
||||
of generated for each change.
|
||||
|
||||
=item B<PKCS5V2>
|
||||
|
||||
Traces PKCS#5 v2 key generation.
|
||||
|
||||
=item B<PKCS12_KEYGEN>
|
||||
|
||||
Traces PKCS#12 key generation.
|
||||
|
||||
=item B<PKCS12_DECRYPT>
|
||||
|
||||
Traces PKCS#12 decryption.
|
||||
|
||||
=item B<X509V3_POLICY>
|
||||
|
||||
Generates the complete policy tree at various points during X.509 v3
|
||||
policy evaluation.
|
||||
Traces everything.
|
||||
|
||||
=item B<BN_CTX>
|
||||
|
||||
|
@ -136,9 +151,9 @@ Traces BIGNUM context operations.
|
|||
|
||||
Traces CMP client and server activity.
|
||||
|
||||
=item B<STORE>
|
||||
=item B<CONF>
|
||||
|
||||
Traces STORE operations.
|
||||
Show details about provider and engine configuration.
|
||||
|
||||
=item B<DECODER>
|
||||
|
||||
|
@ -148,16 +163,81 @@ Traces decoder operations.
|
|||
|
||||
Traces encoder operations.
|
||||
|
||||
=item B<REF_COUNT>
|
||||
=item B<ENGINE_REF_COUNT>
|
||||
|
||||
Traces decrementing certain ASN.1 structure references.
|
||||
Reference counts in the ENGINE structure will be monitored with a line
|
||||
of generated for each change.
|
||||
|
||||
=item B<ENGINE_TABLE>
|
||||
|
||||
The function that is used by RSA, DSA (etc) code to select registered
|
||||
ENGINEs, cache defaults and functional references (etc), will generate
|
||||
debugging summaries.
|
||||
|
||||
=item B<HTTP>
|
||||
|
||||
Traces the HTTP client and server, such as messages being sent and received.
|
||||
|
||||
=item B<INIT>
|
||||
|
||||
Traces OpenSSL library initialization and cleanup.
|
||||
|
||||
=item B<PKCS12_DECRYPT>
|
||||
|
||||
Traces PKCS#12 decryption.
|
||||
|
||||
=item B<PKCS12_KEYGEN>
|
||||
|
||||
Traces PKCS#12 key generation.
|
||||
|
||||
=item B<PKCS5V2>
|
||||
|
||||
Traces PKCS#5 v2 key generation.
|
||||
|
||||
=item B<PROVIDER>
|
||||
|
||||
Traces various operations that are performed on OpenSSL providers during their
|
||||
handling by the library (see L<provider(7)>), such as initialisation, tear down,
|
||||
parameter and capability retrieval, self-test, and so on.
|
||||
|
||||
=item B<QUERY>
|
||||
|
||||
Traces operation related to addition, removal, and fetching of methods
|
||||
in the so-called method store, that holds pointers to functions provided
|
||||
by various providers.
|
||||
|
||||
=item B<REF_COUNT>
|
||||
|
||||
Traces reference count changes in various structures,
|
||||
including C<BIO>, C<DH>, C<DSA>, C<EC_KEY>, C<ECX_KEY>,
|
||||
C<EVP_PKEY>, C<EVP_SKEY>, C<RSA>, C<SSL>, C<SSL_CTX>, C<SSL_SESSION>,
|
||||
C<X509_CRL>, C<X509_STORE>, C<X509>, and some others.
|
||||
|
||||
=item B<STORE>
|
||||
|
||||
Traces STORE operations.
|
||||
|
||||
=item B<TLS>
|
||||
|
||||
Traces the TLS/SSL protocol.
|
||||
|
||||
=item B<TLS_CIPHER>
|
||||
|
||||
Traces the ciphers used by the TLS/SSL protocol.
|
||||
|
||||
=item B<TRACE>
|
||||
|
||||
Traces the OpenSSL trace API itself.
|
||||
|
||||
=item B<X509V3_POLICY>
|
||||
|
||||
Generates the complete policy tree at various points during X.509 v3
|
||||
policy evaluation.
|
||||
|
||||
=back
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<OPENSSL_WIN32_UTF8>
|
||||
|
||||
If set, then L<UI_OpenSSL(3)> returns UTF-8 encoded strings, rather than
|
||||
|
@ -166,41 +246,35 @@ the L<openssl(1)> program also transcodes the command-line parameters
|
|||
from the current code page to UTF-8.
|
||||
This environment variable is only checked on Microsoft Windows platforms.
|
||||
|
||||
=item B<OPENSSL_armcap>, B<OPENSSL_ia32cap>, B<OPENSSL_ppccap>, B<OPENSSL_riscvcap>, B<OPENSSL_s390xcap>, B<OPENSSL_sparcv9cap>
|
||||
|
||||
OpenSSL supports a number of different algorithm implementations for
|
||||
various machines and, by default, it determines which to use based on the
|
||||
processor capabilities and run time feature enquiry. These environment
|
||||
variables can be used to exert more control over this selection process.
|
||||
See L<OPENSSL_ia32cap(3)>, L<OPENSSL_riscvcap(3)>, and L<OPENSSL_s390xcap(3)>.
|
||||
|
||||
These variables are not considered security-sensitive.
|
||||
|
||||
=item B<OSSL_QFILTER>
|
||||
|
||||
Used to set a QUIC qlog filter specification. See L<openssl-qlog(7)>.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<QLOGDIR>
|
||||
|
||||
Specifies a QUIC qlog output directory. See L<openssl-qlog(7)>.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<RANDFILE>
|
||||
|
||||
The state file for the random number generator.
|
||||
This should not be needed in normal use.
|
||||
See L<RAND_load_file(3)>.
|
||||
|
||||
=item B<SSL_CERT_DIR>, B<SSL_CERT_FILE>
|
||||
|
||||
Specify the default directory or file containing CA certificates.
|
||||
See L<SSL_CTX_load_verify_locations(3)>.
|
||||
|
||||
=item B<TSGET>
|
||||
|
||||
Additional arguments for the L<tsget(1)> command.
|
||||
|
||||
=item B<OPENSSL_ia32cap>, B<OPENSSL_sparcv9cap>, B<OPENSSL_ppccap>, B<OPENSSL_armcap>, B<OPENSSL_s390xcap>, B<OPENSSL_riscvcap>
|
||||
|
||||
OpenSSL supports a number of different algorithm implementations for
|
||||
various machines and, by default, it determines which to use based on the
|
||||
processor capabilities and run time feature enquiry. These environment
|
||||
variables can be used to exert more control over this selection process.
|
||||
See L<OPENSSL_ia32cap(3)>, L<OPENSSL_s390xcap(3)> and L<OPENSSL_riscvcap(3)>.
|
||||
|
||||
=item B<NO_PROXY>, B<HTTPS_PROXY>, B<HTTP_PROXY>
|
||||
|
||||
Specify a proxy hostname.
|
||||
See L<OSSL_HTTP_parse_url(3)>.
|
||||
|
||||
=item B<QLOGDIR>
|
||||
|
||||
Specifies a QUIC qlog output directory. See L<openssl-qlog(7)>.
|
||||
|
||||
=item B<OSSL_QFILTER>
|
||||
|
||||
Used to set a QUIC qlog filter specification. See L<openssl-qlog(7)>.
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<SSLKEYLOGFILE>
|
||||
|
||||
|
@ -214,6 +288,49 @@ the exchanged keys during an SSL session, it allows any available party with
|
|||
read access to the file to decrypt application traffic sent over that session.
|
||||
Use of this feature should be restricted to test and debug environments only.
|
||||
|
||||
This variable is considered a security-sensitive environment variable.
|
||||
|
||||
=item B<SSL_CERT_DIR>, B<SSL_CERT_FILE>
|
||||
|
||||
Specify the default directory or file containing CA certificates.
|
||||
See L<SSL_CTX_load_verify_locations(3)>.
|
||||
|
||||
These variables are considered security-sensitive environment variables,
|
||||
except in L<openssl-rehash(1)>, where B<SSL_CERT_DIR> is not considered
|
||||
security-sensitive.
|
||||
|
||||
=item B<SSL_CIPHER>
|
||||
|
||||
Used by L<openssl-s_time(1)> in case B<-cipher> option (that allows modifying
|
||||
TLSv1.2 and below cipher list sent by the client) is not provided,
|
||||
for specification of the aforementioned ciphers.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=item B<TSGET>
|
||||
|
||||
Additional arguments for the L<tsget(1)> command.
|
||||
|
||||
This variable is not considered security-sensitive.
|
||||
|
||||
=back
|
||||
|
||||
=head1 HISTORY
|
||||
|
||||
This section contains environment variables that are no longer considered
|
||||
by the OpenSSL libraries and commands.
|
||||
|
||||
=over 4
|
||||
|
||||
=item B<HARNESS_OSSL_PREFIX>
|
||||
|
||||
This environment variable, existed in OpenSSL versions from 1.1.1 up to 3.5,
|
||||
allowed specification of a prefix prepended to each line sent to the I<stdout>
|
||||
by L<openssl(1)>, used by the test harness to avoid commingling the command
|
||||
under test output with the output for the TAP consumer.
|
||||
|
||||
This variable was not considered security-sensitive.
|
||||
|
||||
=back
|
||||
|
||||
=head1 COPYRIGHT
|
||||
|
|
|
@ -442,6 +442,30 @@ its argument I<mdname>. This signifies that no digest has to be specified
|
|||
with the corresponding signature operation, but may be specified as an
|
||||
option.
|
||||
|
||||
=item "ri-type" (B<OSSL_PKEY_PARAM_CMS_RI_TYPE>) <integer>
|
||||
|
||||
The value should be the CMS RecipientInfo type for the given key, for example
|
||||
B<CMS_RECIPINFO_KEM> or B<CMS_RECIPINFO_AGREE>.
|
||||
The value that can be given through this parameter is found in
|
||||
F<< <openssl/cms.h> >>, with the macros having names starting with
|
||||
C<CMS_RECIPINFO_>.
|
||||
|
||||
CMS will query this parameter first to determine the RecipientInfo type. If
|
||||
this parameter is not filled in, CMS will check for known key types and map
|
||||
them to the appropriate RecipientInfo type. Otherwise, CMS will default to
|
||||
using B<CMS_RECIPINFO_TRANS>.
|
||||
|
||||
=item "kemri-kdf-alg" (B<OSSL_PKEY_PARAM_CMS_KEMRI_KDF_ALGORITHM>) <UTF8 string>
|
||||
|
||||
The value should be the DER-encoded X509_ALGOR for the default KDF for this key
|
||||
if it supports the KEMRecipientInfo (B<CMS_RECIPINFO_KEM>) type.
|
||||
|
||||
Any KDF that takes B<OSSL_KDF_PARAM_KEY> and B<OSSL_KDF_PARAM_INFO> parameters
|
||||
and is otherwise fully defined by its OID can be used, for example B<HKDF-SHA256>.
|
||||
|
||||
If B<OSSL_PKEY_PARAM_CMS_KEMRI_KDF_ALGORITHM> is not implemented, B<HKDF-SHA256>
|
||||
will be used as the default KDF.
|
||||
|
||||
=back
|
||||
|
||||
The OpenSSL FIPS provider also supports the following parameters:
|
||||
|
|
|
@ -1347,3 +1347,5 @@ OBJ_SLH_DSA_SHAKE_256f_WITH_SHAKE256="\x60\x86\x48\x01\x65\x03\x04\x03\x2E"
|
|||
OBJ_HKDF_SHA256="\x2A\x86\x48\x86\xF7\x0D\x01\x09\x10\x03\x1C"
|
||||
OBJ_HKDF_SHA384="\x2A\x86\x48\x86\xF7\x0D\x01\x09\x10\x03\x1D"
|
||||
OBJ_HKDF_SHA512="\x2A\x86\x48\x86\xF7\x0D\x01\x09\x10\x03\x1E"
|
||||
OBJ_id_smime_ori="\x2A\x86\x48\x86\xF7\x0D\x01\x09\x10\x0D"
|
||||
OBJ_id_smime_ori_kem="\x2A\x86\x48\x86\xF7\x0D\x01\x09\x10\x0D\x03"
|
||||
|
|
|
@ -10,6 +10,18 @@
|
|||
#ifndef _CRYPTO_THREADS_COMMON_H_
|
||||
# define _CRYPTO_THREADS_COMMON_H_
|
||||
|
||||
# if defined(__apple_build_version__) && __apple_build_version__ < 6000000
|
||||
/*
|
||||
* OS/X 10.7 and 10.8 had a weird version of clang which has __ATOMIC_ACQUIRE and
|
||||
* __ATOMIC_ACQ_REL but which expects only one parameter for __atomic_is_lock_free()
|
||||
* rather than two which has signature __atomic_is_lock_free(sizeof(_Atomic(T))).
|
||||
* All of this makes impossible to use __atomic_is_lock_free here.
|
||||
*
|
||||
* See: https://github.com/llvm/llvm-project/commit/a4c2602b714e6c6edb98164550a5ae829b2de760
|
||||
*/
|
||||
# define BROKEN_CLANG_ATOMICS
|
||||
# endif
|
||||
|
||||
typedef enum {
|
||||
CRYPTO_THREAD_LOCAL_RCU_KEY = 0,
|
||||
CRYPTO_THREAD_LOCAL_DRBG_PRIV_KEY,
|
||||
|
|
|
@ -0,0 +1,65 @@
|
|||
/*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#ifndef _CRYPTO_THREADS_LOCK_CONTENTION_H_
|
||||
# define _CRYPTO_THREADS_LOCK_CONTENTION_H_
|
||||
|
||||
# include <openssl/configuration.h>
|
||||
|
||||
# if defined(OPENSSL_THREADS) && !defined(CRYPTO_TDEBUG) && !defined(OPENSSL_SYS_WINDOWS)
|
||||
|
||||
# include "internal/threads_common.h"
|
||||
|
||||
# if defined(OPENSSL_NO_STDIO)
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
# warning "RWLOCK CONTENTION REPORTING NOT SUPPORTED, Disabling"
|
||||
# undef REPORT_RWLOCK_CONTENTION
|
||||
# endif
|
||||
# endif
|
||||
|
||||
# include <pthread.h>
|
||||
|
||||
# ifdef REPORT_RWLOCK_CONTENTION
|
||||
|
||||
void ossl_init_rwlock_contention_data(void);
|
||||
void ossl_free_rwlock_contention_data(void);
|
||||
int ossl_rwlock_rdlock(pthread_rwlock_t *);
|
||||
int ossl_rwlock_wrlock(pthread_rwlock_t *);
|
||||
int ossl_rwlock_unlock(pthread_rwlock_t *);
|
||||
|
||||
# else /* !REPORT_RWLOCK_CONTENTION */
|
||||
|
||||
static inline void ossl_init_rwlock_contention_data(void)
|
||||
{
|
||||
}
|
||||
|
||||
static inline void ossl_free_rwlock_contention_data(void)
|
||||
{
|
||||
}
|
||||
|
||||
static inline int ossl_rwlock_rdlock(pthread_rwlock_t *rwlock)
|
||||
{
|
||||
return pthread_rwlock_rdlock(rwlock);
|
||||
}
|
||||
|
||||
static inline int ossl_rwlock_wrlock(pthread_rwlock_t *rwlock)
|
||||
{
|
||||
return pthread_rwlock_wrlock(rwlock);
|
||||
}
|
||||
|
||||
static inline int ossl_rwlock_unlock(pthread_rwlock_t *rwlock)
|
||||
{
|
||||
return pthread_rwlock_unlock(rwlock);
|
||||
}
|
||||
|
||||
# endif /* REPORT_RWLOCK_CONTENTION */
|
||||
|
||||
# endif /* OPENSSL_THREADS && !CRYPTO_TDEBUG && !OPENSSL_SYS_WINDOWS */
|
||||
|
||||
#endif /* _CRYPTO_THREADS_LOCK_CONTENTION_H_ */
|
|
@ -70,6 +70,7 @@ CMS_ContentInfo *CMS_ContentInfo_new_ex(OSSL_LIB_CTX *libctx, const char *propq)
|
|||
# define CMS_RECIPINFO_KEK 2
|
||||
# define CMS_RECIPINFO_PASS 3
|
||||
# define CMS_RECIPINFO_OTHER 4
|
||||
# define CMS_RECIPINFO_KEM 5
|
||||
|
||||
/* S/MIME related flags */
|
||||
|
||||
|
@ -401,6 +402,14 @@ int CMS_RecipientInfo_kari_decrypt(CMS_ContentInfo *cms,
|
|||
int CMS_SharedInfo_encode(unsigned char **pder, X509_ALGOR *kekalg,
|
||||
ASN1_OCTET_STRING *ukm, int keylen);
|
||||
|
||||
int CMS_RecipientInfo_kemri_cert_cmp(CMS_RecipientInfo *ri, X509 *cert);
|
||||
int CMS_RecipientInfo_kemri_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pk);
|
||||
EVP_CIPHER_CTX *CMS_RecipientInfo_kemri_get0_ctx(CMS_RecipientInfo *ri);
|
||||
X509_ALGOR *CMS_RecipientInfo_kemri_get0_kdf_alg(CMS_RecipientInfo *ri);
|
||||
int CMS_RecipientInfo_kemri_set_ukm(CMS_RecipientInfo *ri,
|
||||
const unsigned char *ukm,
|
||||
int ukmLength);
|
||||
|
||||
/* Backward compatibility for spelling errors. */
|
||||
# define CMS_R_UNKNOWN_DIGEST_ALGORITM CMS_R_UNKNOWN_DIGEST_ALGORITHM
|
||||
# define CMS_R_UNSUPPORTED_RECPIENTINFO_TYPE \
|
||||
|
|
|
@ -67,6 +67,7 @@
|
|||
# define CMS_R_NOT_A_SIGNED_RECEIPT 165
|
||||
# define CMS_R_NOT_ENCRYPTED_DATA 122
|
||||
# define CMS_R_NOT_KEK 123
|
||||
# define CMS_R_NOT_KEM 197
|
||||
# define CMS_R_NOT_KEY_AGREEMENT 181
|
||||
# define CMS_R_NOT_KEY_TRANSPORT 124
|
||||
# define CMS_R_NOT_PWRI 177
|
||||
|
@ -106,10 +107,12 @@
|
|||
# define CMS_R_UNKNOWN_CIPHER 148
|
||||
# define CMS_R_UNKNOWN_DIGEST_ALGORITHM 149
|
||||
# define CMS_R_UNKNOWN_ID 150
|
||||
# define CMS_R_UNKNOWN_KDF_ALGORITHM 198
|
||||
# define CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM 151
|
||||
# define CMS_R_UNSUPPORTED_CONTENT_ENCRYPTION_ALGORITHM 194
|
||||
# define CMS_R_UNSUPPORTED_CONTENT_TYPE 152
|
||||
# define CMS_R_UNSUPPORTED_ENCRYPTION_TYPE 192
|
||||
# define CMS_R_UNSUPPORTED_KDF_ALGORITHM 199
|
||||
# define CMS_R_UNSUPPORTED_KEK_ALGORITHM 153
|
||||
# define CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM 179
|
||||
# define CMS_R_UNSUPPORTED_LABEL_SOURCE 193
|
||||
|
|
|
@ -778,6 +778,10 @@
|
|||
#define NID_id_smime_cti 195
|
||||
#define OBJ_id_smime_cti OBJ_SMIME,6L
|
||||
|
||||
#define SN_id_smime_ori "id-smime-ori"
|
||||
#define NID_id_smime_ori 1499
|
||||
#define OBJ_id_smime_ori OBJ_SMIME,13L
|
||||
|
||||
#define SN_id_smime_mod_cms "id-smime-mod-cms"
|
||||
#define NID_id_smime_mod_cms 196
|
||||
#define OBJ_id_smime_mod_cms OBJ_id_smime_mod,1L
|
||||
|
@ -1113,6 +1117,10 @@
|
|||
#define NID_id_smime_cti_ets_proofOfCreation 256
|
||||
#define OBJ_id_smime_cti_ets_proofOfCreation OBJ_id_smime_cti,6L
|
||||
|
||||
#define SN_id_smime_ori_kem "id-smime-ori-kem"
|
||||
#define NID_id_smime_ori_kem 1500
|
||||
#define OBJ_id_smime_ori_kem OBJ_id_smime_ori,3L
|
||||
|
||||
#define LN_friendlyName "friendlyName"
|
||||
#define NID_friendlyName 156
|
||||
#define OBJ_friendlyName OBJ_pkcs9,20L
|
||||
|
|
|
@ -0,0 +1,16 @@
|
|||
-- Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
--
|
||||
-- Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
-- this file except in compliance with the License. You can obtain a copy
|
||||
-- in the file LICENSE in the source distribution or at
|
||||
-- https://www.openssl.org/source/license.html
|
||||
|
||||
-- -------------------------------------------------------------------
|
||||
-- Taken from https://datatracker.ietf.org/doc/rfc8619/
|
||||
|
||||
id-smime OBJECT IDENTIFIER ::= { 1 2 840 113549 1 9 16 }
|
||||
id-alg OBJECT IDENTIFIER ::= { id-smime 3 }
|
||||
|
||||
id-alg-hkdf-with-sha256 OBJECT IDENTIFIER ::= { id-alg 28 }
|
||||
id-alg-hkdf-with-sha384 OBJECT IDENTIFIER ::= { id-alg 29 }
|
||||
id-alg-hkdf-with-sha512 OBJECT IDENTIFIER ::= { id-alg 30 }
|
|
@ -127,9 +127,20 @@ IF[{- !$disabled{'slh-dsa'} -}]
|
|||
DEPEND[$DER_SLH_DSA_H]=oids_to_c.pm SLH_DSA.asn1
|
||||
ENDIF
|
||||
|
||||
#----- HKDF
|
||||
$DER_HKDF_H=$INCDIR/der_hkdf.h
|
||||
$DER_HKDF_GEN=der_hkdf_gen.c
|
||||
|
||||
GENERATE[$DER_HKDF_GEN]=der_hkdf_gen.c.in
|
||||
DEPEND[$DER_HKDF_GEN]=oids_to_c.pm HKDF.asn1
|
||||
|
||||
DEPEND[${DER_HKDF_GEN/.c/.o}]=$DER_HKDF_H
|
||||
GENERATE[$DER_HKDF_H]=$INCDIR/der_hkdf.h.in
|
||||
DEPEND[$DER_HKDF_H]=oids_to_c.pm HKDF.asn1
|
||||
|
||||
#----- Conclusion
|
||||
|
||||
$COMMON= $DER_RSA_COMMON $DER_DIGESTS_GEN $DER_WRAP_GEN
|
||||
$COMMON= $DER_RSA_COMMON $DER_DIGESTS_GEN $DER_WRAP_GEN $DER_HKDF_GEN
|
||||
|
||||
IF[{- !$disabled{dsa} -}]
|
||||
$COMMON = $COMMON $DER_DSA_GEN $DER_DSA_AUX
|
||||
|
|
|
@ -0,0 +1,19 @@
|
|||
/*
|
||||
* {- join("\n * ", @autowarntext) -}
|
||||
*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#include "prov/der_hkdf.h"
|
||||
|
||||
/* Well known OIDs precompiled */
|
||||
{-
|
||||
$OUT = oids_to_c::process_leaves('providers/common/der/HKDF.asn1',
|
||||
{ dir => $config{sourcedir},
|
||||
filter => \&oids_to_c::filter_to_C });
|
||||
-}
|
|
@ -0,0 +1,19 @@
|
|||
/*
|
||||
* {- join("\n * ", @autowarntext) -}
|
||||
*
|
||||
* Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
*
|
||||
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
||||
* this file except in compliance with the License. You can obtain a copy
|
||||
* in the file LICENSE in the source distribution or at
|
||||
* https://www.openssl.org/source/license.html
|
||||
*/
|
||||
|
||||
#include "internal/der.h"
|
||||
|
||||
/* Well known OIDs precompiled */
|
||||
{-
|
||||
$OUT = oids_to_c::process_leaves('providers/common/der/HKDF.asn1',
|
||||
{ dir => $config{sourcedir},
|
||||
filter => \&oids_to_c::filter_to_H });
|
||||
-}
|
|
@ -47,6 +47,7 @@ IF[{- !$disabled{'ml-kem'} -}]
|
|||
SOURCE[$TLS_ML_KEM_HYBRID_GOAL]=mlx_kmgmt.c
|
||||
ENDIF
|
||||
SOURCE[$ML_KEM_GOAL]=ml_kem_kmgmt.c
|
||||
DEPEND[ml_kem_kmgmt.o]=../../common/include/prov/der_hkdf.h
|
||||
ENDIF
|
||||
|
||||
SOURCE[$RSA_GOAL]=rsa_kmgmt.c
|
||||
|
|
|
@ -19,9 +19,13 @@ use OpenSSL::paramnames qw(produce_param_decoder);
|
|||
#include <openssl/rand.h>
|
||||
#include <openssl/self_test.h>
|
||||
#include <openssl/param_build.h>
|
||||
#include <openssl/cms.h>
|
||||
#include "crypto/ml_kem.h"
|
||||
#include "internal/fips.h"
|
||||
#include "internal/param_build_set.h"
|
||||
#include "internal/sizes.h"
|
||||
#include "prov/der_hkdf.h"
|
||||
#include "prov/der_wrap.h"
|
||||
#include "prov/implementations.h"
|
||||
#include "prov/providercommon.h"
|
||||
#include "prov/provider_ctx.h"
|
||||
|
@ -494,6 +498,8 @@ static int ml_kem_import(void *vkey, int selection, const OSSL_PARAM params[])
|
|||
['PKEY_PARAM_PRIV_KEY', 'privkey', 'octet_string'],
|
||||
['PKEY_PARAM_PUB_KEY', 'pubkey', 'octet_string'],
|
||||
['PKEY_PARAM_ENCODED_PUBLIC_KEY', 'encpubkey', 'octet_string'],
|
||||
['PKEY_PARAM_CMS_RI_TYPE', 'ri_type', 'int'],
|
||||
['PKEY_PARAM_CMS_KEMRI_KDF_ALGORITHM', 'kemri_kdf_alg', 'octet_string'],
|
||||
)); -}
|
||||
|
||||
static const OSSL_PARAM *ml_kem_gettable_params(void *provctx)
|
||||
|
@ -612,6 +618,36 @@ static int ml_kem_get_params(void *vkey, OSSL_PARAM params[])
|
|||
&ossl_ml_kem_encode_seed))
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef OPENSSL_NO_CMS
|
||||
if (p.ri_type != NULL && !OSSL_PARAM_set_int(p.ri_type, CMS_RECIPINFO_KEM))
|
||||
return 0;
|
||||
|
||||
if (p.kemri_kdf_alg != NULL) {
|
||||
uint8_t aid_buf[OSSL_MAX_ALGORITHM_ID_SIZE];
|
||||
int ret;
|
||||
size_t aid_len = 0;
|
||||
WPACKET pkt;
|
||||
uint8_t *aid = NULL;
|
||||
|
||||
ret = WPACKET_init_der(&pkt, aid_buf, sizeof(aid_buf));
|
||||
ret &= ossl_DER_w_begin_sequence(&pkt, -1)
|
||||
&& ossl_DER_w_precompiled(&pkt, -1, ossl_der_oid_id_alg_hkdf_with_sha256,
|
||||
sizeof(ossl_der_oid_id_alg_hkdf_with_sha256))
|
||||
&& ossl_DER_w_end_sequence(&pkt, -1);
|
||||
if (ret && WPACKET_finish(&pkt)) {
|
||||
WPACKET_get_total_written(&pkt, &aid_len);
|
||||
aid = WPACKET_get_curr(&pkt);
|
||||
}
|
||||
WPACKET_cleanup(&pkt);
|
||||
if (!ret)
|
||||
return 0;
|
||||
if (aid != NULL && aid_len != 0 &&
|
||||
!OSSL_PARAM_set_octet_string(p.kemri_kdf_alg, aid, aid_len))
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
|
|
@ -53,7 +53,7 @@ my ($no_des, $no_dh, $no_dsa, $no_ec, $no_ec2m, $no_rc2, $no_zlib)
|
|||
|
||||
$no_rc2 = 1 if disabled("legacy");
|
||||
|
||||
plan tests => 31;
|
||||
plan tests => 32;
|
||||
|
||||
ok(run(test(["pkcs7_test"])), "test pkcs7");
|
||||
|
||||
|
@ -1528,3 +1528,44 @@ subtest "sign and verify with multiple keys" => sub {
|
|||
"verify both signature signatures with root");
|
||||
is(compare($smcont, $out2), 0, "compare original message with verified message");
|
||||
};
|
||||
|
||||
subtest "ML-KEM KEMRecipientInfo tests for CMS" => sub {
|
||||
plan tests => 5;
|
||||
|
||||
SKIP: {
|
||||
skip "ML-KEM is not supported in this build", 5
|
||||
if disabled("ml-kem") || $no_pqc;
|
||||
|
||||
ok(run(app(["openssl", "cms", @prov, "-encrypt", "-in", $smcont,
|
||||
"-out", "mlkem512.cms",
|
||||
"-recip", catfile($smdir, "sm_mlkem512.pem"),
|
||||
"-aes-256-gcm", "-keyid" ])),
|
||||
"CMS encrypt with ML-KEM-512 and default KDF");
|
||||
|
||||
ok(run(app(["openssl", "cms", @prov, "-decrypt", "-in", "mlkem512.cms",
|
||||
"-out", "mlkem512.txt", "-recip", catfile($smdir, "sm_mlkem512.pem")]))
|
||||
&& compare_text($smcont, "mlkem512.txt") == 0,
|
||||
"CMS decrypt with ML-KEM-512 and default KDF");
|
||||
|
||||
ok(run(app(["openssl", "cms", @prov, "-encrypt", "-in", $smcont,
|
||||
"-out", "mlkem512_mlkem768.cms",
|
||||
"-recip", catfile($smdir, "sm_mlkem512.pem"),
|
||||
"-recip_kdf", "HKDF-SHA512",
|
||||
"-recip", catfile($smdir, "sm_mlkem768.pem"),
|
||||
"-recip_ukm", "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f",
|
||||
"-aes-256-gcm", "-keyid" ])),
|
||||
"CMS encrypt to multiple with ML-KEM and explicit KDF and UKM");
|
||||
|
||||
ok(run(app(["openssl", "cms", @prov, "-decrypt", "-in", "mlkem512_mlkem768.cms",
|
||||
"-out", "mlkem512-2.txt",
|
||||
"-recip", catfile($smdir, "sm_mlkem512.pem")]))
|
||||
&& compare_text($smcont, "mlkem512-2.txt") == 0,
|
||||
"CMS decrypt with ML-KEM-512 and explicit KDF");
|
||||
|
||||
ok(run(app(["openssl", "cms", @prov, "-decrypt", "-in", "mlkem512_mlkem768.cms",
|
||||
"-out", "mlkem768-2.txt",
|
||||
"-recip", catfile($smdir, "sm_mlkem768.pem")]))
|
||||
&& compare_text($smcont, "mlkem768-2.txt") == 0,
|
||||
"CMS decrypt with ML-KEM-768 and using UKM");
|
||||
}
|
||||
};
|
||||
|
|
|
@ -24,6 +24,6 @@ test -d "$QUICHE_TARGET_PATH" || exit 1
|
|||
|
||||
"$QUICHE_TARGET_PATH/debug/quiche-server" --cert "$SRCTOP/test/certs/servercert.pem" \
|
||||
--key "$SRCTOP/test/certs/serverkey.pem" --disable-gso \
|
||||
--http-version HTTP/0.9 --root "$SRCTOP" --no-grease --disable-hystart &
|
||||
--http-version HTTP/0.9 --root "$SRCTOP" --no-grease --disable-hystart > quiche_server_log 2>&1 &
|
||||
|
||||
echo $! >server.pid
|
||||
|
|
|
@ -48,7 +48,6 @@ echo "------------------------------------------------------------------"
|
|||
cmake $SRCTOP/gost-engine -DOPENSSL_ROOT_DIR="$OPENSSL_ROOT_DIR" -DOPENSSL_ENGINES_DIR="$OPENSSL_ROOT_DIR/engines"
|
||||
make
|
||||
export CTEST_OUTPUT_ON_FAILURE=1
|
||||
export HARNESS_OSSL_PREFIX=''
|
||||
export OPENSSL_ENGINES="$PWD/bin"
|
||||
export OPENSSL_APP="$O_EXE/openssl"
|
||||
make test
|
||||
|
|
|
@ -65,7 +65,6 @@ fi
|
|||
echo " CWD: $PWD"
|
||||
liboqs_DIR=$SRCTOP/oqs-provider/.local cmake $SRCTOP/oqs-provider -DOPENSSL_ROOT_DIR="$OPENSSL_ROOT_DIR" -B _build && cmake --build _build
|
||||
export CTEST_OUTPUT_ON_FAILURE=1
|
||||
export HARNESS_OSSL_PREFIX=''
|
||||
export OPENSSL_APP="$O_EXE/openssl"
|
||||
export OPENSSL_MODULES=$PWD/_build/lib
|
||||
export OQS_PROVIDER_TESTSCRIPTS=$SRCTOP/oqs-provider/scripts
|
||||
|
|
|
@ -63,9 +63,8 @@ echo "------------------------------------------------------------------"
|
|||
echo "Running tests"
|
||||
echo "------------------------------------------------------------------"
|
||||
|
||||
# The OpenSSL app uses ${HARNESS_OSSL_PREFIX} as a prefix for its standard output
|
||||
# For maintenance reasons and simplicity we only run test with kryoptic token
|
||||
HARNESS_OSSL_PREFIX= meson test -C $PKCS11_PROVIDER_BUILDDIR --suite=kryoptic
|
||||
meson test -C $PKCS11_PROVIDER_BUILDDIR --suite=kryoptic
|
||||
|
||||
if [ $? -ne 0 ]; then
|
||||
cat $PKCS11_PROVIDER_BUILDDIR/meson-logs/testlog.txt
|
||||
|
|
|
@ -58,6 +58,14 @@ keyUsage = critical, digitalSignature
|
|||
basicConstraints = CA:FALSE
|
||||
keyUsage = critical, keyAgreement
|
||||
|
||||
[ kem_cert ]
|
||||
|
||||
# These extensions are added when 'ca' signs a request for an end-entity
|
||||
# KEM certificate, for which only key encipherment makes sense
|
||||
|
||||
basicConstraints = CA:FALSE
|
||||
keyUsage = critical, keyEncipherment
|
||||
|
||||
[ codesign_cert ]
|
||||
|
||||
# These extensions are added when 'ca' signs a request for a code-signing
|
||||
|
|
|
@ -80,3 +80,7 @@ gen sm_slhdsa_shake_128s.pem "/CN=Test SMIME EE SLH-DSA-SHAKE-128s" \
|
|||
$OPENSSL genpkey -algorithm SLH-DSA-SHAKE-256s -out sm_slhdsa_shake_256s.pem
|
||||
gen sm_slhdsa_shake_256s.pem "/CN=Test SMIME EE SLH-DSA-SHAKE-256s" \
|
||||
signer_cert >>sm_slhdsa_shake_256s.pem
|
||||
$OPENSSL genpkey -algorithm ML-KEM-512 -out sm_mlkem512.pem
|
||||
gen sm_mlkem512.pem "/CN=Test SMIME EE ML-KEM-512" kem_cert >>sm_mlkem512.pem
|
||||
$OPENSSL genpkey -algorithm ML-KEM-768 -out sm_mlkem768.pem
|
||||
gen sm_mlkem768.pem "/CN=Test SMIME EE ML-KEM-768" kem_cert >>sm_mlkem768.pem
|
||||
|
|
|
@ -0,0 +1,70 @@
|
|||
-----BEGIN PRIVATE KEY-----
|
||||
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
|
||||
SD8=
|
||||
-----END PRIVATE KEY-----
|
||||
-----BEGIN CERTIFICATE-----
|
||||
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
|
||||
-----END CERTIFICATE-----
|
|
@ -0,0 +1,94 @@
|
|||
-----BEGIN PRIVATE KEY-----
|
||||
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
|
||||
be8=
|
||||
-----END PRIVATE KEY-----
|
||||
-----BEGIN CERTIFICATE-----
|
||||
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
|
||||
-----END CERTIFICATE-----
|
|
@ -1,4 +1,4 @@
|
|||
#!/bin/bash
|
||||
#!/bin/bash -eu
|
||||
# Copyright 2025 The OpenSSL Project Authors. All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License 2.0 (the "License").
|
||||
|
@ -15,29 +15,21 @@
|
|||
#
|
||||
TEMPDIR=$(mktemp -d /tmp/contention.XXXXXX)
|
||||
|
||||
LOGFILE=$1
|
||||
trap "rm -rf $TEMPDIR" EXIT
|
||||
|
||||
if [ ! -f $LOGFILE ]
|
||||
then
|
||||
echo "No log file found"
|
||||
exit 1
|
||||
fi
|
||||
LOGFILEBASE=$(basename $LOGFILE)
|
||||
|
||||
echo "Splitting files"
|
||||
echo "Splitting files" > /dev/stderr
|
||||
|
||||
#
|
||||
#start by splitting the log into separate stack traces
|
||||
#
|
||||
mkdir $TEMPDIR/individual_files
|
||||
cp $LOGFILE $TEMPDIR/individual_files/$LOGFILEBASE
|
||||
mkdir "$TEMPDIR/individual_files"
|
||||
cat "$@" > "$TEMPDIR/individual_files/log"
|
||||
pushd $TEMPDIR/individual_files/ > /dev/null
|
||||
awk '
|
||||
BEGIN {RS = ""; FS = "\n"}
|
||||
{file_num++; print > ("stacktrace" file_num ".txt")}' ./$LOGFILEBASE
|
||||
{file_num++; print > ("stacktrace" file_num ".txt")}' ./log
|
||||
popd > /dev/null
|
||||
rm $TEMPDIR/individual_files/$LOGFILEBASE
|
||||
rm -f $TEMPDIR/individual_files/log
|
||||
|
||||
#
|
||||
# Make some associative arrays to track our stats
|
||||
|
@ -46,9 +38,9 @@ declare -A filenames
|
|||
declare -A total_latency
|
||||
declare -A latency_counts
|
||||
|
||||
echo "Gathering latencies"
|
||||
echo "Gathering latencies" > /dev/stderr
|
||||
FILECOUNT=$(ls $TEMPDIR/individual_files/stacktrace*.* | wc -l)
|
||||
let currentidx=0
|
||||
currentidx=0
|
||||
|
||||
#
|
||||
# Look at every stack trace, get and record its latency, and hash value
|
||||
|
@ -61,8 +53,8 @@ do
|
|||
#now compute its sha1sum
|
||||
SHA1SUM=$(sha1sum $i | awk '{print $1}')
|
||||
filenames["$SHA1SUM"]=$i
|
||||
let CUR_LATENCY=0
|
||||
let LATENCY_COUNT=0
|
||||
CUR_LATENCY=0
|
||||
LATENCY_COUNT=0
|
||||
|
||||
#
|
||||
# If we already have a latency total for this hash value
|
||||
|
@ -71,8 +63,8 @@ do
|
|||
#
|
||||
if [[ -v total_latency["$SHA1SUM"] ]]
|
||||
then
|
||||
let CUR_LATENCY=${total_latency["$SHA1SUM"]}
|
||||
let LATENCY_COUNT=${latency_counts["$SHA1SUM"]}
|
||||
CUR_LATENCY=${total_latency["$SHA1SUM"]}
|
||||
LATENCY_COUNT=${latency_counts["$SHA1SUM"]}
|
||||
fi
|
||||
|
||||
#
|
||||
|
@ -81,8 +73,8 @@ do
|
|||
#
|
||||
total_latency["$SHA1SUM"]=$(dc -e "$CUR_LATENCY $LATENCY + p")
|
||||
latency_counts["$SHA1SUM"]=$(dc -e "$LATENCY_COUNT 1 + p")
|
||||
echo -e -n "FILE $currentidx/$FILECOUNT \r"
|
||||
let currentidx=$currentidx+1
|
||||
echo -e -n "FILE $currentidx/$FILECOUNT \r" > /dev/stderr
|
||||
currentidx=$((currentidx + 1))
|
||||
done
|
||||
|
||||
#
|
||||
|
|
|
@ -42,11 +42,13 @@ our($opt_u);
|
|||
our($opt_v);
|
||||
our($opt_c);
|
||||
our($opt_i);
|
||||
our($opt_a);
|
||||
|
||||
# Print usage message and exit.
|
||||
sub help {
|
||||
print <<EOF;
|
||||
Find small errors (nits) in documentation. Options:
|
||||
-a List undocumented env vars
|
||||
-c List undocumented commands, undocumented options and unimplemented options.
|
||||
-d Detailed list of undocumented (implies -u)
|
||||
-e Detailed list of new undocumented (implies -v)
|
||||
|
@ -62,7 +64,7 @@ EOF
|
|||
exit;
|
||||
}
|
||||
|
||||
getopts('cdehlm:noiuv');
|
||||
getopts('acdehlm:noiuv');
|
||||
|
||||
help() if $opt_h;
|
||||
$opt_u = 1 if $opt_d;
|
||||
|
@ -74,8 +76,8 @@ die "Cannot use both -d and -e"
|
|||
|
||||
# We only need to check c, l, n, u and v.
|
||||
# Options d, e, o imply one of the above.
|
||||
die "Need one of -[cdehlnouv] flags.\n"
|
||||
unless $opt_c or $opt_l or $opt_n or $opt_u or $opt_v;
|
||||
die "Need one of -[acdehlnouv] flags.\n"
|
||||
unless $opt_a or $opt_c or $opt_l or $opt_n or $opt_u or $opt_v;
|
||||
|
||||
|
||||
my $temp = '/tmp/docnits.txt';
|
||||
|
@ -1275,6 +1277,104 @@ sub checkflags {
|
|||
}
|
||||
}
|
||||
|
||||
sub check_env_vars {
|
||||
# initialized with the list of "untracable" variables
|
||||
my %env_list = ("SSL_CERT_FILE" => 1);
|
||||
my @env_files;
|
||||
my @except_env_files = (
|
||||
"$config{sourcedir}/providers/implementations/keymgmt/template_kmgmt.c",
|
||||
"$config{sourcedir}/providers/implementations/kem/template_kem.c",
|
||||
"$config{sourcedir}/Makefile.in",
|
||||
);
|
||||
my @env_headers;
|
||||
my @env_macro;
|
||||
|
||||
# look for source files
|
||||
find(sub { push @env_files, $File::Find::name if /\.c$|\.in$/; },
|
||||
$config{sourcedir});
|
||||
|
||||
foreach my $filename (@env_files) {
|
||||
next if $filename =~ /test\/|demos\//
|
||||
|| grep { $_ eq $filename } @except_env_files;
|
||||
|
||||
open my $fh, '<', $filename or die "Can't open $filename: $!";
|
||||
while (my $line = <$fh>) {
|
||||
# for windows
|
||||
# for .in files
|
||||
$env_list{$1} = 1 if ($line =~ /GetEnvironmentVariableW\([\s\S]*"([^"]+)",/
|
||||
|| $line =~ /\$ENV\{([^}"']+)\}/);
|
||||
# this also handles ossl_safe_getenv
|
||||
if ($line =~ /getenv\(([^()\s]+)\)/) {
|
||||
my $env1 = $1;
|
||||
if ($env1 =~ /"([^"]+)"/) {
|
||||
$env_list{$1} = 1;
|
||||
} elsif ($env1 =~ /([A-Z0-9_])/) {
|
||||
push(@env_macro, $env1);
|
||||
}
|
||||
}
|
||||
# match ternary operators; $1 - true, $2 - false
|
||||
if ($line =~ /env\(\s*[^?]+\?\s*([^:( ]+)\s*:\s*([^(]+)\s*\)/) {
|
||||
my ($env1, $env2) = ($1, $2);
|
||||
# if it's a string just add to the list
|
||||
# otherwise look for the constant value later
|
||||
if ($env1 =~ /"([^"]+)"/) {
|
||||
$env_list{$1} = 1;
|
||||
} else {
|
||||
push(@env_macro, $env1);
|
||||
}
|
||||
if ($env2 =~ /"([^"]+)"/) {
|
||||
$env_list{$1} = 1;
|
||||
} else {
|
||||
push(@env_macro, $env2);
|
||||
}
|
||||
}
|
||||
}
|
||||
close $fh;
|
||||
}
|
||||
|
||||
# look for constants in header files
|
||||
find(sub { push @env_headers, $File::Find::name if /\.h$/; },
|
||||
$config{sourcedir});
|
||||
|
||||
foreach my $filename (@env_headers) {
|
||||
open my $fh, '<', $filename or die "Can't open $filename: $!";
|
||||
while (my $line = <$fh>) {
|
||||
foreach my $em (@env_macro) {
|
||||
$env_list{$1} = 1 if ($line =~ /define\s+\Q$em\E\s+"(\S+)"/);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
# need to save the value before starting to delete from the hash
|
||||
my $number_of_env = scalar keys %env_list;
|
||||
|
||||
# check for env vars in pod files
|
||||
foreach ( files(TAGS => [ 'manual' ]) ) {
|
||||
my %podinfo = extract_pod_info($_, { debug => $debug });
|
||||
my $contents = $podinfo{contents};
|
||||
|
||||
# openssl-env.pod does not have ENVIRONMENT section, but the whole file
|
||||
# is about environment variables
|
||||
if ( $contents =~ /=head1 ENVIRONMENT(.*)=head1/ms ) {
|
||||
$contents = $1;
|
||||
} elsif ( $_ !~ /openssl-env.pod/ ) {
|
||||
next;
|
||||
}
|
||||
|
||||
for my $env_name (keys %env_list) {
|
||||
delete($env_list{$env_name}) if $contents =~ $env_name;
|
||||
}
|
||||
}
|
||||
|
||||
print "Number of env vars found:".$number_of_env."\n" if $debug;
|
||||
$number_of_env = scalar keys %env_list;
|
||||
if ($number_of_env != 0) {
|
||||
print "Undocumented environment variables:\n";
|
||||
print join("\n", sort keys %env_list)."\n";
|
||||
err("Total:".$number_of_env."\n");
|
||||
}
|
||||
}
|
||||
|
||||
##
|
||||
## MAIN()
|
||||
## Do the work requested by the various getopt flags.
|
||||
|
@ -1373,6 +1473,10 @@ if ( $opt_n ) {
|
|||
}
|
||||
}
|
||||
|
||||
if ( $opt_a ) {
|
||||
check_env_vars();
|
||||
}
|
||||
|
||||
checkstate();
|
||||
|
||||
if ( $opt_u || $opt_v) {
|
||||
|
|
|
@ -123,6 +123,7 @@
|
|||
-T CMAC_CTX
|
||||
-T CMS_AuthenticatedData
|
||||
-T CMS_CertificateChoices
|
||||
-T CMS_CMSORIforKEMOtherInfo
|
||||
-T CMS_CompressedData
|
||||
-T CMS_ContentInfo
|
||||
-T CMS_DigestedData
|
||||
|
@ -133,6 +134,7 @@
|
|||
-T CMS_IssuerAndSerialNumber
|
||||
-T CMS_KEKIdentifier
|
||||
-T CMS_KEKRecipientInfo
|
||||
-T CMS_KEMRecipientInfo
|
||||
-T CMS_KeyAgreeRecipientIdentifier
|
||||
-T CMS_KeyAgreeRecipientInfo
|
||||
-T CMS_KeyTransRecipientInfo
|
||||
|
|
|
@ -5931,3 +5931,8 @@ i2d_PKCS8PrivateKey ? 3_6_0 EXIST::FUNCTION:
|
|||
OSSL_PARAM_set_octet_string_or_ptr ? 3_6_0 EXIST::FUNCTION:
|
||||
OSSL_STORE_LOADER_settable_ctx_params ? 3_6_0 EXIST::FUNCTION:
|
||||
X509_CRL_get0_tbs_sigalg ? 3_6_0 EXIST::FUNCTION:
|
||||
CMS_RecipientInfo_kemri_cert_cmp ? 3_6_0 EXIST::FUNCTION:CMS
|
||||
CMS_RecipientInfo_kemri_set0_pkey ? 3_6_0 EXIST::FUNCTION:CMS
|
||||
CMS_RecipientInfo_kemri_get0_ctx ? 3_6_0 EXIST::FUNCTION:CMS
|
||||
CMS_RecipientInfo_kemri_get0_kdf_alg ? 3_6_0 EXIST::FUNCTION:CMS
|
||||
CMS_RecipientInfo_kemri_set_ukm ? 3_6_0 EXIST::FUNCTION:CMS
|
||||
|
|
|
@ -290,7 +290,6 @@ CMS_RecipientEncryptedKey_get0_id(3)
|
|||
CMS_RecipientInfo_get0_pkey_ctx(3)
|
||||
CMS_RecipientInfo_kari_decrypt(3)
|
||||
CMS_RecipientInfo_kari_get0_alg(3)
|
||||
CMS_RecipientInfo_kari_get0_ctx(3)
|
||||
CMS_RecipientInfo_kari_get0_orig_id(3)
|
||||
CMS_RecipientInfo_kari_get0_reks(3)
|
||||
CMS_RecipientInfo_kari_orig_id_cmp(3)
|
||||
|
|
|
@ -2,11 +2,15 @@
|
|||
# that don't appear in lib*.num -- because they are define's, in
|
||||
# assembly language, etc.
|
||||
#
|
||||
OPENSSL_armcap environment
|
||||
OPENSSL_ia32cap environment
|
||||
OPENSSL_s390xcap environment
|
||||
OPENSSL_ppccap environment
|
||||
OPENSSL_riscvcap environment
|
||||
OPENSSL_s390xcap environment
|
||||
OPENSSL_sparcv9cap environment
|
||||
OPENSSL_MALLOC_FD environment
|
||||
OPENSSL_MALLOC_FAILURES environment
|
||||
OPENSSL_MALLOC_SEED environment
|
||||
OPENSSL_instrument_bus assembler
|
||||
OPENSSL_instrument_bus2 assembler
|
||||
#
|
||||
|
|
|
@ -465,17 +465,15 @@ sub run {
|
|||
|
||||
$ENV{HARNESS_OSSL_LEVEL} = $level + 1;
|
||||
|
||||
# The dance we do with $? is the same dance the Unix shells appear to
|
||||
# do. For example, a program that gets aborted (and therefore signals
|
||||
# SIGABRT = 6) will appear to exit with the code 134. We mimic this
|
||||
# to make it easier to compare with a manual run of the command.
|
||||
if ($opts{capture} || defined($opts{prefix})) {
|
||||
# We prefix the output with "# " in non-capture mode by default to avoid
|
||||
# its interpretation by the TAP consumer.
|
||||
my $default_prefix = $opts{capture} ? "" : "# ";
|
||||
my $pipe;
|
||||
local $_;
|
||||
|
||||
open($pipe, '-|', "$prefix$cmd") or die "Can't start command: $!";
|
||||
while(<$pipe>) {
|
||||
my $l = ($opts{prefix} // "") . $_;
|
||||
my $l = ($opts{prefix} // $default_prefix) . $_;
|
||||
if ($opts{capture}) {
|
||||
push @r, $l;
|
||||
} else {
|
||||
|
@ -483,11 +481,11 @@ sub run {
|
|||
}
|
||||
}
|
||||
close $pipe;
|
||||
} else {
|
||||
$ENV{HARNESS_OSSL_PREFIX} = "# ";
|
||||
system("$prefix$cmd");
|
||||
delete $ENV{HARNESS_OSSL_PREFIX};
|
||||
}
|
||||
|
||||
# The dance we do with $? is the same dance the Unix shells appear to
|
||||
# do. For example, a program that gets aborted (and therefore signals
|
||||
# SIGABRT = 6) will appear to exit with the code 134. We mimic this
|
||||
# to make it easier to compare with a manual run of the command.
|
||||
$e = ($? & 0x7f) ? ($? & 0x7f)|0x80 : ($? >> 8);
|
||||
$r = $hooks{exit_checker}->($e);
|
||||
if ($opts{statusvar}) {
|
||||
|
|
|
@ -315,6 +315,8 @@ my %params = (
|
|||
'PKEY_PARAM_FIPS_KEY_CHECK' => "key-check",
|
||||
'PKEY_PARAM_ALGORITHM_ID' => '*ALG_PARAM_ALGORITHM_ID',
|
||||
'PKEY_PARAM_ALGORITHM_ID_PARAMS' => '*ALG_PARAM_ALGORITHM_ID_PARAMS',
|
||||
'PKEY_PARAM_CMS_RI_TYPE' => "ri-type", # integer
|
||||
'PKEY_PARAM_CMS_KEMRI_KDF_ALGORITHM' => "kemri-kdf-alg",
|
||||
|
||||
# Diffie-Hellman/DSA Parameters
|
||||
'PKEY_PARAM_FFC_P' => "p",
|
||||
|
|
Loading…
Reference in New Issue