summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/lib/libcrypto/cms/cms_asn1.c403
-rw-r--r--src/lib/libcrypto/cms/cms_att.c152
-rw-r--r--src/lib/libcrypto/cms/cms_cd.c82
-rw-r--r--src/lib/libcrypto/cms/cms_dd.c99
-rw-r--r--src/lib/libcrypto/cms/cms_enc.c213
-rw-r--r--src/lib/libcrypto/cms/cms_env.c903
-rw-r--r--src/lib/libcrypto/cms/cms_err.c294
-rw-r--r--src/lib/libcrypto/cms/cms_ess.c337
-rw-r--r--src/lib/libcrypto/cms/cms_io.c88
-rw-r--r--src/lib/libcrypto/cms/cms_kari.c414
-rw-r--r--src/lib/libcrypto/cms/cms_lcl.h437
-rw-r--r--src/lib/libcrypto/cms/cms_lib.c587
-rw-r--r--src/lib/libcrypto/cms/cms_pwri.c394
-rw-r--r--src/lib/libcrypto/cms/cms_sd.c926
-rw-r--r--src/lib/libcrypto/cms/cms_smime.c843
15 files changed, 6172 insertions, 0 deletions
diff --git a/src/lib/libcrypto/cms/cms_asn1.c b/src/lib/libcrypto/cms/cms_asn1.c
new file mode 100644
index 0000000000..993ea6b219
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_asn1.c
@@ -0,0 +1,403 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include <openssl/asn1t.h>
11#include <openssl/pem.h>
12#include <openssl/x509v3.h>
13#include <openssl/cms.h>
14#include "cms_lcl.h"
15
16
17ASN1_SEQUENCE(CMS_IssuerAndSerialNumber) = {
18 ASN1_SIMPLE(CMS_IssuerAndSerialNumber, issuer, X509_NAME),
19 ASN1_SIMPLE(CMS_IssuerAndSerialNumber, serialNumber, ASN1_INTEGER)
20} ASN1_SEQUENCE_END(CMS_IssuerAndSerialNumber)
21
22ASN1_SEQUENCE(CMS_OtherCertificateFormat) = {
23 ASN1_SIMPLE(CMS_OtherCertificateFormat, otherCertFormat, ASN1_OBJECT),
24 ASN1_OPT(CMS_OtherCertificateFormat, otherCert, ASN1_ANY)
25} static_ASN1_SEQUENCE_END(CMS_OtherCertificateFormat)
26
27ASN1_CHOICE(CMS_CertificateChoices) = {
28 ASN1_SIMPLE(CMS_CertificateChoices, d.certificate, X509),
29 ASN1_IMP(CMS_CertificateChoices, d.extendedCertificate, ASN1_SEQUENCE, 0),
30 ASN1_IMP(CMS_CertificateChoices, d.v1AttrCert, ASN1_SEQUENCE, 1),
31 ASN1_IMP(CMS_CertificateChoices, d.v2AttrCert, ASN1_SEQUENCE, 2),
32 ASN1_IMP(CMS_CertificateChoices, d.other, CMS_OtherCertificateFormat, 3)
33} ASN1_CHOICE_END(CMS_CertificateChoices)
34
35ASN1_CHOICE(CMS_SignerIdentifier) = {
36 ASN1_SIMPLE(CMS_SignerIdentifier, d.issuerAndSerialNumber, CMS_IssuerAndSerialNumber),
37 ASN1_IMP(CMS_SignerIdentifier, d.subjectKeyIdentifier, ASN1_OCTET_STRING, 0)
38} static_ASN1_CHOICE_END(CMS_SignerIdentifier)
39
40ASN1_NDEF_SEQUENCE(CMS_EncapsulatedContentInfo) = {
41 ASN1_SIMPLE(CMS_EncapsulatedContentInfo, eContentType, ASN1_OBJECT),
42 ASN1_NDEF_EXP_OPT(CMS_EncapsulatedContentInfo, eContent, ASN1_OCTET_STRING_NDEF, 0)
43} static_ASN1_NDEF_SEQUENCE_END(CMS_EncapsulatedContentInfo)
44
45/* Minor tweak to operation: free up signer key, cert */
46static int cms_si_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
47 void *exarg)
48{
49 if (operation == ASN1_OP_FREE_POST) {
50 CMS_SignerInfo *si = (CMS_SignerInfo *)*pval;
51 EVP_PKEY_free(si->pkey);
52 X509_free(si->signer);
53 EVP_MD_CTX_free(si->mctx);
54 }
55 return 1;
56}
57
58ASN1_SEQUENCE_cb(CMS_SignerInfo, cms_si_cb) = {
59 ASN1_EMBED(CMS_SignerInfo, version, INT32),
60 ASN1_SIMPLE(CMS_SignerInfo, sid, CMS_SignerIdentifier),
61 ASN1_SIMPLE(CMS_SignerInfo, digestAlgorithm, X509_ALGOR),
62 ASN1_IMP_SET_OF_OPT(CMS_SignerInfo, signedAttrs, X509_ATTRIBUTE, 0),
63 ASN1_SIMPLE(CMS_SignerInfo, signatureAlgorithm, X509_ALGOR),
64 ASN1_SIMPLE(CMS_SignerInfo, signature, ASN1_OCTET_STRING),
65 ASN1_IMP_SET_OF_OPT(CMS_SignerInfo, unsignedAttrs, X509_ATTRIBUTE, 1)
66} ASN1_SEQUENCE_END_cb(CMS_SignerInfo, CMS_SignerInfo)
67
68ASN1_SEQUENCE(CMS_OtherRevocationInfoFormat) = {
69 ASN1_SIMPLE(CMS_OtherRevocationInfoFormat, otherRevInfoFormat, ASN1_OBJECT),
70 ASN1_OPT(CMS_OtherRevocationInfoFormat, otherRevInfo, ASN1_ANY)
71} static_ASN1_SEQUENCE_END(CMS_OtherRevocationInfoFormat)
72
73ASN1_CHOICE(CMS_RevocationInfoChoice) = {
74 ASN1_SIMPLE(CMS_RevocationInfoChoice, d.crl, X509_CRL),
75 ASN1_IMP(CMS_RevocationInfoChoice, d.other, CMS_OtherRevocationInfoFormat, 1)
76} ASN1_CHOICE_END(CMS_RevocationInfoChoice)
77
78ASN1_NDEF_SEQUENCE(CMS_SignedData) = {
79 ASN1_EMBED(CMS_SignedData, version, INT32),
80 ASN1_SET_OF(CMS_SignedData, digestAlgorithms, X509_ALGOR),
81 ASN1_SIMPLE(CMS_SignedData, encapContentInfo, CMS_EncapsulatedContentInfo),
82 ASN1_IMP_SET_OF_OPT(CMS_SignedData, certificates, CMS_CertificateChoices, 0),
83 ASN1_IMP_SET_OF_OPT(CMS_SignedData, crls, CMS_RevocationInfoChoice, 1),
84 ASN1_SET_OF(CMS_SignedData, signerInfos, CMS_SignerInfo)
85} ASN1_NDEF_SEQUENCE_END(CMS_SignedData)
86
87ASN1_SEQUENCE(CMS_OriginatorInfo) = {
88 ASN1_IMP_SET_OF_OPT(CMS_OriginatorInfo, certificates, CMS_CertificateChoices, 0),
89 ASN1_IMP_SET_OF_OPT(CMS_OriginatorInfo, crls, CMS_RevocationInfoChoice, 1)
90} static_ASN1_SEQUENCE_END(CMS_OriginatorInfo)
91
92ASN1_NDEF_SEQUENCE(CMS_EncryptedContentInfo) = {
93 ASN1_SIMPLE(CMS_EncryptedContentInfo, contentType, ASN1_OBJECT),
94 ASN1_SIMPLE(CMS_EncryptedContentInfo, contentEncryptionAlgorithm, X509_ALGOR),
95 ASN1_IMP_OPT(CMS_EncryptedContentInfo, encryptedContent, ASN1_OCTET_STRING_NDEF, 0)
96} static_ASN1_NDEF_SEQUENCE_END(CMS_EncryptedContentInfo)
97
98ASN1_SEQUENCE(CMS_KeyTransRecipientInfo) = {
99 ASN1_EMBED(CMS_KeyTransRecipientInfo, version, INT32),
100 ASN1_SIMPLE(CMS_KeyTransRecipientInfo, rid, CMS_SignerIdentifier),
101 ASN1_SIMPLE(CMS_KeyTransRecipientInfo, keyEncryptionAlgorithm, X509_ALGOR),
102 ASN1_SIMPLE(CMS_KeyTransRecipientInfo, encryptedKey, ASN1_OCTET_STRING)
103} ASN1_SEQUENCE_END(CMS_KeyTransRecipientInfo)
104
105ASN1_SEQUENCE(CMS_OtherKeyAttribute) = {
106 ASN1_SIMPLE(CMS_OtherKeyAttribute, keyAttrId, ASN1_OBJECT),
107 ASN1_OPT(CMS_OtherKeyAttribute, keyAttr, ASN1_ANY)
108} ASN1_SEQUENCE_END(CMS_OtherKeyAttribute)
109
110ASN1_SEQUENCE(CMS_RecipientKeyIdentifier) = {
111 ASN1_SIMPLE(CMS_RecipientKeyIdentifier, subjectKeyIdentifier, ASN1_OCTET_STRING),
112 ASN1_OPT(CMS_RecipientKeyIdentifier, date, ASN1_GENERALIZEDTIME),
113 ASN1_OPT(CMS_RecipientKeyIdentifier, other, CMS_OtherKeyAttribute)
114} ASN1_SEQUENCE_END(CMS_RecipientKeyIdentifier)
115
116ASN1_CHOICE(CMS_KeyAgreeRecipientIdentifier) = {
117 ASN1_SIMPLE(CMS_KeyAgreeRecipientIdentifier, d.issuerAndSerialNumber, CMS_IssuerAndSerialNumber),
118 ASN1_IMP(CMS_KeyAgreeRecipientIdentifier, d.rKeyId, CMS_RecipientKeyIdentifier, 0)
119} static_ASN1_CHOICE_END(CMS_KeyAgreeRecipientIdentifier)
120
121static int cms_rek_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
122 void *exarg)
123{
124 CMS_RecipientEncryptedKey *rek = (CMS_RecipientEncryptedKey *)*pval;
125 if (operation == ASN1_OP_FREE_POST) {
126 EVP_PKEY_free(rek->pkey);
127 }
128 return 1;
129}
130
131ASN1_SEQUENCE_cb(CMS_RecipientEncryptedKey, cms_rek_cb) = {
132 ASN1_SIMPLE(CMS_RecipientEncryptedKey, rid, CMS_KeyAgreeRecipientIdentifier),
133 ASN1_SIMPLE(CMS_RecipientEncryptedKey, encryptedKey, ASN1_OCTET_STRING)
134} ASN1_SEQUENCE_END_cb(CMS_RecipientEncryptedKey, CMS_RecipientEncryptedKey)
135
136ASN1_SEQUENCE(CMS_OriginatorPublicKey) = {
137 ASN1_SIMPLE(CMS_OriginatorPublicKey, algorithm, X509_ALGOR),
138 ASN1_SIMPLE(CMS_OriginatorPublicKey, publicKey, ASN1_BIT_STRING)
139} ASN1_SEQUENCE_END(CMS_OriginatorPublicKey)
140
141ASN1_CHOICE(CMS_OriginatorIdentifierOrKey) = {
142 ASN1_SIMPLE(CMS_OriginatorIdentifierOrKey, d.issuerAndSerialNumber, CMS_IssuerAndSerialNumber),
143 ASN1_IMP(CMS_OriginatorIdentifierOrKey, d.subjectKeyIdentifier, ASN1_OCTET_STRING, 0),
144 ASN1_IMP(CMS_OriginatorIdentifierOrKey, d.originatorKey, CMS_OriginatorPublicKey, 1)
145} static_ASN1_CHOICE_END(CMS_OriginatorIdentifierOrKey)
146
147static int cms_kari_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
148 void *exarg)
149{
150 CMS_KeyAgreeRecipientInfo *kari = (CMS_KeyAgreeRecipientInfo *)*pval;
151 if (operation == ASN1_OP_NEW_POST) {
152 kari->ctx = EVP_CIPHER_CTX_new();
153 if (kari->ctx == NULL)
154 return 0;
155 EVP_CIPHER_CTX_set_flags(kari->ctx, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW);
156 kari->pctx = NULL;
157 } else if (operation == ASN1_OP_FREE_POST) {
158 EVP_PKEY_CTX_free(kari->pctx);
159 EVP_CIPHER_CTX_free(kari->ctx);
160 }
161 return 1;
162}
163
164ASN1_SEQUENCE_cb(CMS_KeyAgreeRecipientInfo, cms_kari_cb) = {
165 ASN1_EMBED(CMS_KeyAgreeRecipientInfo, version, INT32),
166 ASN1_EXP(CMS_KeyAgreeRecipientInfo, originator, CMS_OriginatorIdentifierOrKey, 0),
167 ASN1_EXP_OPT(CMS_KeyAgreeRecipientInfo, ukm, ASN1_OCTET_STRING, 1),
168 ASN1_SIMPLE(CMS_KeyAgreeRecipientInfo, keyEncryptionAlgorithm, X509_ALGOR),
169 ASN1_SEQUENCE_OF(CMS_KeyAgreeRecipientInfo, recipientEncryptedKeys, CMS_RecipientEncryptedKey)
170} ASN1_SEQUENCE_END_cb(CMS_KeyAgreeRecipientInfo, CMS_KeyAgreeRecipientInfo)
171
172ASN1_SEQUENCE(CMS_KEKIdentifier) = {
173 ASN1_SIMPLE(CMS_KEKIdentifier, keyIdentifier, ASN1_OCTET_STRING),
174 ASN1_OPT(CMS_KEKIdentifier, date, ASN1_GENERALIZEDTIME),
175 ASN1_OPT(CMS_KEKIdentifier, other, CMS_OtherKeyAttribute)
176} static_ASN1_SEQUENCE_END(CMS_KEKIdentifier)
177
178ASN1_SEQUENCE(CMS_KEKRecipientInfo) = {
179 ASN1_EMBED(CMS_KEKRecipientInfo, version, INT32),
180 ASN1_SIMPLE(CMS_KEKRecipientInfo, kekid, CMS_KEKIdentifier),
181 ASN1_SIMPLE(CMS_KEKRecipientInfo, keyEncryptionAlgorithm, X509_ALGOR),
182 ASN1_SIMPLE(CMS_KEKRecipientInfo, encryptedKey, ASN1_OCTET_STRING)
183} ASN1_SEQUENCE_END(CMS_KEKRecipientInfo)
184
185ASN1_SEQUENCE(CMS_PasswordRecipientInfo) = {
186 ASN1_EMBED(CMS_PasswordRecipientInfo, version, INT32),
187 ASN1_IMP_OPT(CMS_PasswordRecipientInfo, keyDerivationAlgorithm, X509_ALGOR, 0),
188 ASN1_SIMPLE(CMS_PasswordRecipientInfo, keyEncryptionAlgorithm, X509_ALGOR),
189 ASN1_SIMPLE(CMS_PasswordRecipientInfo, encryptedKey, ASN1_OCTET_STRING)
190} ASN1_SEQUENCE_END(CMS_PasswordRecipientInfo)
191
192ASN1_SEQUENCE(CMS_OtherRecipientInfo) = {
193 ASN1_SIMPLE(CMS_OtherRecipientInfo, oriType, ASN1_OBJECT),
194 ASN1_OPT(CMS_OtherRecipientInfo, oriValue, ASN1_ANY)
195} static_ASN1_SEQUENCE_END(CMS_OtherRecipientInfo)
196
197/* Free up RecipientInfo additional data */
198static int cms_ri_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
199 void *exarg)
200{
201 if (operation == ASN1_OP_FREE_PRE) {
202 CMS_RecipientInfo *ri = (CMS_RecipientInfo *)*pval;
203 if (ri->type == CMS_RECIPINFO_TRANS) {
204 CMS_KeyTransRecipientInfo *ktri = ri->d.ktri;
205 EVP_PKEY_free(ktri->pkey);
206 X509_free(ktri->recip);
207 EVP_PKEY_CTX_free(ktri->pctx);
208 } else if (ri->type == CMS_RECIPINFO_KEK) {
209 CMS_KEKRecipientInfo *kekri = ri->d.kekri;
210 OPENSSL_clear_free(kekri->key, kekri->keylen);
211 } else if (ri->type == CMS_RECIPINFO_PASS) {
212 CMS_PasswordRecipientInfo *pwri = ri->d.pwri;
213 OPENSSL_clear_free(pwri->pass, pwri->passlen);
214 }
215 }
216 return 1;
217}
218
219ASN1_CHOICE_cb(CMS_RecipientInfo, cms_ri_cb) = {
220 ASN1_SIMPLE(CMS_RecipientInfo, d.ktri, CMS_KeyTransRecipientInfo),
221 ASN1_IMP(CMS_RecipientInfo, d.kari, CMS_KeyAgreeRecipientInfo, 1),
222 ASN1_IMP(CMS_RecipientInfo, d.kekri, CMS_KEKRecipientInfo, 2),
223 ASN1_IMP(CMS_RecipientInfo, d.pwri, CMS_PasswordRecipientInfo, 3),
224 ASN1_IMP(CMS_RecipientInfo, d.ori, CMS_OtherRecipientInfo, 4)
225} ASN1_CHOICE_END_cb(CMS_RecipientInfo, CMS_RecipientInfo, type)
226
227ASN1_NDEF_SEQUENCE(CMS_EnvelopedData) = {
228 ASN1_EMBED(CMS_EnvelopedData, version, INT32),
229 ASN1_IMP_OPT(CMS_EnvelopedData, originatorInfo, CMS_OriginatorInfo, 0),
230 ASN1_SET_OF(CMS_EnvelopedData, recipientInfos, CMS_RecipientInfo),
231 ASN1_SIMPLE(CMS_EnvelopedData, encryptedContentInfo, CMS_EncryptedContentInfo),
232 ASN1_IMP_SET_OF_OPT(CMS_EnvelopedData, unprotectedAttrs, X509_ATTRIBUTE, 1)
233} ASN1_NDEF_SEQUENCE_END(CMS_EnvelopedData)
234
235ASN1_NDEF_SEQUENCE(CMS_DigestedData) = {
236 ASN1_EMBED(CMS_DigestedData, version, INT32),
237 ASN1_SIMPLE(CMS_DigestedData, digestAlgorithm, X509_ALGOR),
238 ASN1_SIMPLE(CMS_DigestedData, encapContentInfo, CMS_EncapsulatedContentInfo),
239 ASN1_SIMPLE(CMS_DigestedData, digest, ASN1_OCTET_STRING)
240} ASN1_NDEF_SEQUENCE_END(CMS_DigestedData)
241
242ASN1_NDEF_SEQUENCE(CMS_EncryptedData) = {
243 ASN1_EMBED(CMS_EncryptedData, version, INT32),
244 ASN1_SIMPLE(CMS_EncryptedData, encryptedContentInfo, CMS_EncryptedContentInfo),
245 ASN1_IMP_SET_OF_OPT(CMS_EncryptedData, unprotectedAttrs, X509_ATTRIBUTE, 1)
246} ASN1_NDEF_SEQUENCE_END(CMS_EncryptedData)
247
248ASN1_NDEF_SEQUENCE(CMS_AuthenticatedData) = {
249 ASN1_EMBED(CMS_AuthenticatedData, version, INT32),
250 ASN1_IMP_OPT(CMS_AuthenticatedData, originatorInfo, CMS_OriginatorInfo, 0),
251 ASN1_SET_OF(CMS_AuthenticatedData, recipientInfos, CMS_RecipientInfo),
252 ASN1_SIMPLE(CMS_AuthenticatedData, macAlgorithm, X509_ALGOR),
253 ASN1_IMP(CMS_AuthenticatedData, digestAlgorithm, X509_ALGOR, 1),
254 ASN1_SIMPLE(CMS_AuthenticatedData, encapContentInfo, CMS_EncapsulatedContentInfo),
255 ASN1_IMP_SET_OF_OPT(CMS_AuthenticatedData, authAttrs, X509_ALGOR, 2),
256 ASN1_SIMPLE(CMS_AuthenticatedData, mac, ASN1_OCTET_STRING),
257 ASN1_IMP_SET_OF_OPT(CMS_AuthenticatedData, unauthAttrs, X509_ALGOR, 3)
258} static_ASN1_NDEF_SEQUENCE_END(CMS_AuthenticatedData)
259
260ASN1_NDEF_SEQUENCE(CMS_CompressedData) = {
261 ASN1_EMBED(CMS_CompressedData, version, INT32),
262 ASN1_SIMPLE(CMS_CompressedData, compressionAlgorithm, X509_ALGOR),
263 ASN1_SIMPLE(CMS_CompressedData, encapContentInfo, CMS_EncapsulatedContentInfo),
264} ASN1_NDEF_SEQUENCE_END(CMS_CompressedData)
265
266/* This is the ANY DEFINED BY table for the top level ContentInfo structure */
267
268ASN1_ADB_TEMPLATE(cms_default) = ASN1_EXP(CMS_ContentInfo, d.other, ASN1_ANY, 0);
269
270ASN1_ADB(CMS_ContentInfo) = {
271 ADB_ENTRY(NID_pkcs7_data, ASN1_NDEF_EXP(CMS_ContentInfo, d.data, ASN1_OCTET_STRING_NDEF, 0)),
272 ADB_ENTRY(NID_pkcs7_signed, ASN1_NDEF_EXP(CMS_ContentInfo, d.signedData, CMS_SignedData, 0)),
273 ADB_ENTRY(NID_pkcs7_enveloped, ASN1_NDEF_EXP(CMS_ContentInfo, d.envelopedData, CMS_EnvelopedData, 0)),
274 ADB_ENTRY(NID_pkcs7_digest, ASN1_NDEF_EXP(CMS_ContentInfo, d.digestedData, CMS_DigestedData, 0)),
275 ADB_ENTRY(NID_pkcs7_encrypted, ASN1_NDEF_EXP(CMS_ContentInfo, d.encryptedData, CMS_EncryptedData, 0)),
276 ADB_ENTRY(NID_id_smime_ct_authData, ASN1_NDEF_EXP(CMS_ContentInfo, d.authenticatedData, CMS_AuthenticatedData, 0)),
277 ADB_ENTRY(NID_id_smime_ct_compressedData, ASN1_NDEF_EXP(CMS_ContentInfo, d.compressedData, CMS_CompressedData, 0)),
278} ASN1_ADB_END(CMS_ContentInfo, 0, contentType, 0, &cms_default_tt, NULL);
279
280/* CMS streaming support */
281static int cms_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it,
282 void *exarg)
283{
284 ASN1_STREAM_ARG *sarg = exarg;
285 CMS_ContentInfo *cms = NULL;
286 if (pval)
287 cms = (CMS_ContentInfo *)*pval;
288 else
289 return 1;
290 switch (operation) {
291
292 case ASN1_OP_STREAM_PRE:
293 if (CMS_stream(&sarg->boundary, cms) <= 0)
294 return 0;
295 /* fall thru */
296 case ASN1_OP_DETACHED_PRE:
297 sarg->ndef_bio = CMS_dataInit(cms, sarg->out);
298 if (!sarg->ndef_bio)
299 return 0;
300 break;
301
302 case ASN1_OP_STREAM_POST:
303 case ASN1_OP_DETACHED_POST:
304 if (CMS_dataFinal(cms, sarg->ndef_bio) <= 0)
305 return 0;
306 break;
307
308 }
309 return 1;
310}
311
312ASN1_NDEF_SEQUENCE_cb(CMS_ContentInfo, cms_cb) = {
313 ASN1_SIMPLE(CMS_ContentInfo, contentType, ASN1_OBJECT),
314 ASN1_ADB_OBJECT(CMS_ContentInfo)
315} ASN1_NDEF_SEQUENCE_END_cb(CMS_ContentInfo, CMS_ContentInfo)
316
317/* Specials for signed attributes */
318
319/*
320 * When signing attributes we want to reorder them to match the sorted
321 * encoding.
322 */
323
324ASN1_ITEM_TEMPLATE(CMS_Attributes_Sign) =
325 ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SET_ORDER, 0, CMS_ATTRIBUTES, X509_ATTRIBUTE)
326ASN1_ITEM_TEMPLATE_END(CMS_Attributes_Sign)
327
328/*
329 * When verifying attributes we need to use the received order. So we use
330 * SEQUENCE OF and tag it to SET OF
331 */
332
333ASN1_ITEM_TEMPLATE(CMS_Attributes_Verify) =
334 ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF | ASN1_TFLG_IMPTAG | ASN1_TFLG_UNIVERSAL,
335 V_ASN1_SET, CMS_ATTRIBUTES, X509_ATTRIBUTE)
336ASN1_ITEM_TEMPLATE_END(CMS_Attributes_Verify)
337
338
339
340ASN1_CHOICE(CMS_ReceiptsFrom) = {
341 ASN1_IMP_EMBED(CMS_ReceiptsFrom, d.allOrFirstTier, INT32, 0),
342 ASN1_IMP_SEQUENCE_OF(CMS_ReceiptsFrom, d.receiptList, GENERAL_NAMES, 1)
343} static_ASN1_CHOICE_END(CMS_ReceiptsFrom)
344
345ASN1_SEQUENCE(CMS_ReceiptRequest) = {
346 ASN1_SIMPLE(CMS_ReceiptRequest, signedContentIdentifier, ASN1_OCTET_STRING),
347 ASN1_SIMPLE(CMS_ReceiptRequest, receiptsFrom, CMS_ReceiptsFrom),
348 ASN1_SEQUENCE_OF(CMS_ReceiptRequest, receiptsTo, GENERAL_NAMES)
349} ASN1_SEQUENCE_END(CMS_ReceiptRequest)
350
351ASN1_SEQUENCE(CMS_Receipt) = {
352 ASN1_EMBED(CMS_Receipt, version, INT32),
353 ASN1_SIMPLE(CMS_Receipt, contentType, ASN1_OBJECT),
354 ASN1_SIMPLE(CMS_Receipt, signedContentIdentifier, ASN1_OCTET_STRING),
355 ASN1_SIMPLE(CMS_Receipt, originatorSignatureValue, ASN1_OCTET_STRING)
356} ASN1_SEQUENCE_END(CMS_Receipt)
357
358/*
359 * Utilities to encode the CMS_SharedInfo structure used during key
360 * derivation.
361 */
362
363typedef struct {
364 X509_ALGOR *keyInfo;
365 ASN1_OCTET_STRING *entityUInfo;
366 ASN1_OCTET_STRING *suppPubInfo;
367} CMS_SharedInfo;
368
369ASN1_SEQUENCE(CMS_SharedInfo) = {
370 ASN1_SIMPLE(CMS_SharedInfo, keyInfo, X509_ALGOR),
371 ASN1_EXP_OPT(CMS_SharedInfo, entityUInfo, ASN1_OCTET_STRING, 0),
372 ASN1_EXP_OPT(CMS_SharedInfo, suppPubInfo, ASN1_OCTET_STRING, 2),
373} static_ASN1_SEQUENCE_END(CMS_SharedInfo)
374
375int CMS_SharedInfo_encode(unsigned char **pder, X509_ALGOR *kekalg,
376 ASN1_OCTET_STRING *ukm, int keylen)
377{
378 union {
379 CMS_SharedInfo *pecsi;
380 ASN1_VALUE *a;
381 } intsi = {
382 NULL
383 };
384
385 ASN1_OCTET_STRING oklen;
386 unsigned char kl[4];
387 CMS_SharedInfo ecsi;
388
389 keylen <<= 3;
390 kl[0] = (keylen >> 24) & 0xff;
391 kl[1] = (keylen >> 16) & 0xff;
392 kl[2] = (keylen >> 8) & 0xff;
393 kl[3] = keylen & 0xff;
394 oklen.length = 4;
395 oklen.data = kl;
396 oklen.type = V_ASN1_OCTET_STRING;
397 oklen.flags = 0;
398 ecsi.keyInfo = kekalg;
399 ecsi.entityUInfo = ukm;
400 ecsi.suppPubInfo = &oklen;
401 intsi.pecsi = &ecsi;
402 return ASN1_item_i2d(intsi.a, pder, ASN1_ITEM_rptr(CMS_SharedInfo));
403}
diff --git a/src/lib/libcrypto/cms/cms_att.c b/src/lib/libcrypto/cms/cms_att.c
new file mode 100644
index 0000000000..664e64971b
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_att.c
@@ -0,0 +1,152 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include <openssl/asn1t.h>
11#include <openssl/pem.h>
12#include <openssl/x509v3.h>
13#include <openssl/err.h>
14#include <openssl/cms.h>
15#include "cms_lcl.h"
16
17/* CMS SignedData Attribute utilities */
18
19int CMS_signed_get_attr_count(const CMS_SignerInfo *si)
20{
21 return X509at_get_attr_count(si->signedAttrs);
22}
23
24int CMS_signed_get_attr_by_NID(const CMS_SignerInfo *si, int nid, int lastpos)
25{
26 return X509at_get_attr_by_NID(si->signedAttrs, nid, lastpos);
27}
28
29int CMS_signed_get_attr_by_OBJ(const CMS_SignerInfo *si, const ASN1_OBJECT *obj,
30 int lastpos)
31{
32 return X509at_get_attr_by_OBJ(si->signedAttrs, obj, lastpos);
33}
34
35X509_ATTRIBUTE *CMS_signed_get_attr(const CMS_SignerInfo *si, int loc)
36{
37 return X509at_get_attr(si->signedAttrs, loc);
38}
39
40X509_ATTRIBUTE *CMS_signed_delete_attr(CMS_SignerInfo *si, int loc)
41{
42 return X509at_delete_attr(si->signedAttrs, loc);
43}
44
45int CMS_signed_add1_attr(CMS_SignerInfo *si, X509_ATTRIBUTE *attr)
46{
47 if (X509at_add1_attr(&si->signedAttrs, attr))
48 return 1;
49 return 0;
50}
51
52int CMS_signed_add1_attr_by_OBJ(CMS_SignerInfo *si,
53 const ASN1_OBJECT *obj, int type,
54 const void *bytes, int len)
55{
56 if (X509at_add1_attr_by_OBJ(&si->signedAttrs, obj, type, bytes, len))
57 return 1;
58 return 0;
59}
60
61int CMS_signed_add1_attr_by_NID(CMS_SignerInfo *si,
62 int nid, int type, const void *bytes, int len)
63{
64 if (X509at_add1_attr_by_NID(&si->signedAttrs, nid, type, bytes, len))
65 return 1;
66 return 0;
67}
68
69int CMS_signed_add1_attr_by_txt(CMS_SignerInfo *si,
70 const char *attrname, int type,
71 const void *bytes, int len)
72{
73 if (X509at_add1_attr_by_txt(&si->signedAttrs, attrname, type, bytes, len))
74 return 1;
75 return 0;
76}
77
78void *CMS_signed_get0_data_by_OBJ(CMS_SignerInfo *si, const ASN1_OBJECT *oid,
79 int lastpos, int type)
80{
81 return X509at_get0_data_by_OBJ(si->signedAttrs, oid, lastpos, type);
82}
83
84int CMS_unsigned_get_attr_count(const CMS_SignerInfo *si)
85{
86 return X509at_get_attr_count(si->unsignedAttrs);
87}
88
89int CMS_unsigned_get_attr_by_NID(const CMS_SignerInfo *si, int nid,
90 int lastpos)
91{
92 return X509at_get_attr_by_NID(si->unsignedAttrs, nid, lastpos);
93}
94
95int CMS_unsigned_get_attr_by_OBJ(const CMS_SignerInfo *si,
96 const ASN1_OBJECT *obj, int lastpos)
97{
98 return X509at_get_attr_by_OBJ(si->unsignedAttrs, obj, lastpos);
99}
100
101X509_ATTRIBUTE *CMS_unsigned_get_attr(const CMS_SignerInfo *si, int loc)
102{
103 return X509at_get_attr(si->unsignedAttrs, loc);
104}
105
106X509_ATTRIBUTE *CMS_unsigned_delete_attr(CMS_SignerInfo *si, int loc)
107{
108 return X509at_delete_attr(si->unsignedAttrs, loc);
109}
110
111int CMS_unsigned_add1_attr(CMS_SignerInfo *si, X509_ATTRIBUTE *attr)
112{
113 if (X509at_add1_attr(&si->unsignedAttrs, attr))
114 return 1;
115 return 0;
116}
117
118int CMS_unsigned_add1_attr_by_OBJ(CMS_SignerInfo *si,
119 const ASN1_OBJECT *obj, int type,
120 const void *bytes, int len)
121{
122 if (X509at_add1_attr_by_OBJ(&si->unsignedAttrs, obj, type, bytes, len))
123 return 1;
124 return 0;
125}
126
127int CMS_unsigned_add1_attr_by_NID(CMS_SignerInfo *si,
128 int nid, int type,
129 const void *bytes, int len)
130{
131 if (X509at_add1_attr_by_NID(&si->unsignedAttrs, nid, type, bytes, len))
132 return 1;
133 return 0;
134}
135
136int CMS_unsigned_add1_attr_by_txt(CMS_SignerInfo *si,
137 const char *attrname, int type,
138 const void *bytes, int len)
139{
140 if (X509at_add1_attr_by_txt(&si->unsignedAttrs, attrname,
141 type, bytes, len))
142 return 1;
143 return 0;
144}
145
146void *CMS_unsigned_get0_data_by_OBJ(CMS_SignerInfo *si, ASN1_OBJECT *oid,
147 int lastpos, int type)
148{
149 return X509at_get0_data_by_OBJ(si->unsignedAttrs, oid, lastpos, type);
150}
151
152/* Specific attribute cases */
diff --git a/src/lib/libcrypto/cms/cms_cd.c b/src/lib/libcrypto/cms/cms_cd.c
new file mode 100644
index 0000000000..f05e308418
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_cd.c
@@ -0,0 +1,82 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include <openssl/bio.h>
17#include <openssl/comp.h>
18#include "cms_lcl.h"
19
20#ifdef ZLIB
21
22/* CMS CompressedData Utilities */
23
24CMS_ContentInfo *cms_CompressedData_create(int comp_nid)
25{
26 CMS_ContentInfo *cms;
27 CMS_CompressedData *cd;
28 /*
29 * Will need something cleverer if there is ever more than one
30 * compression algorithm or parameters have some meaning...
31 */
32 if (comp_nid != NID_zlib_compression) {
33 CMSerr(CMS_F_CMS_COMPRESSEDDATA_CREATE,
34 CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
35 return NULL;
36 }
37 cms = CMS_ContentInfo_new();
38 if (cms == NULL)
39 return NULL;
40
41 cd = M_ASN1_new_of(CMS_CompressedData);
42
43 if (cd == NULL)
44 goto err;
45
46 cms->contentType = OBJ_nid2obj(NID_id_smime_ct_compressedData);
47 cms->d.compressedData = cd;
48
49 cd->version = 0;
50
51 X509_ALGOR_set0(cd->compressionAlgorithm,
52 OBJ_nid2obj(NID_zlib_compression), V_ASN1_UNDEF, NULL);
53
54 cd->encapContentInfo->eContentType = OBJ_nid2obj(NID_pkcs7_data);
55
56 return cms;
57
58 err:
59 CMS_ContentInfo_free(cms);
60 return NULL;
61}
62
63BIO *cms_CompressedData_init_bio(CMS_ContentInfo *cms)
64{
65 CMS_CompressedData *cd;
66 const ASN1_OBJECT *compoid;
67 if (OBJ_obj2nid(cms->contentType) != NID_id_smime_ct_compressedData) {
68 CMSerr(CMS_F_CMS_COMPRESSEDDATA_INIT_BIO,
69 CMS_R_CONTENT_TYPE_NOT_COMPRESSED_DATA);
70 return NULL;
71 }
72 cd = cms->d.compressedData;
73 X509_ALGOR_get0(&compoid, NULL, NULL, cd->compressionAlgorithm);
74 if (OBJ_obj2nid(compoid) != NID_zlib_compression) {
75 CMSerr(CMS_F_CMS_COMPRESSEDDATA_INIT_BIO,
76 CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
77 return NULL;
78 }
79 return BIO_new(BIO_f_zlib());
80}
81
82#endif
diff --git a/src/lib/libcrypto/cms/cms_dd.c b/src/lib/libcrypto/cms/cms_dd.c
new file mode 100644
index 0000000000..5da6802fcd
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_dd.c
@@ -0,0 +1,99 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include "cms_lcl.h"
17
18/* CMS DigestedData Utilities */
19
20CMS_ContentInfo *cms_DigestedData_create(const EVP_MD *md)
21{
22 CMS_ContentInfo *cms;
23 CMS_DigestedData *dd;
24 cms = CMS_ContentInfo_new();
25 if (cms == NULL)
26 return NULL;
27
28 dd = M_ASN1_new_of(CMS_DigestedData);
29
30 if (dd == NULL)
31 goto err;
32
33 cms->contentType = OBJ_nid2obj(NID_pkcs7_digest);
34 cms->d.digestedData = dd;
35
36 dd->version = 0;
37 dd->encapContentInfo->eContentType = OBJ_nid2obj(NID_pkcs7_data);
38
39 X509_ALGOR_set_md(dd->digestAlgorithm, md);
40
41 return cms;
42
43 err:
44 CMS_ContentInfo_free(cms);
45 return NULL;
46}
47
48BIO *cms_DigestedData_init_bio(CMS_ContentInfo *cms)
49{
50 CMS_DigestedData *dd;
51 dd = cms->d.digestedData;
52 return cms_DigestAlgorithm_init_bio(dd->digestAlgorithm);
53}
54
55int cms_DigestedData_do_final(CMS_ContentInfo *cms, BIO *chain, int verify)
56{
57 EVP_MD_CTX *mctx = EVP_MD_CTX_new();
58 unsigned char md[EVP_MAX_MD_SIZE];
59 unsigned int mdlen;
60 int r = 0;
61 CMS_DigestedData *dd;
62
63 if (mctx == NULL) {
64 CMSerr(CMS_F_CMS_DIGESTEDDATA_DO_FINAL, ERR_R_MALLOC_FAILURE);
65 goto err;
66 }
67
68 dd = cms->d.digestedData;
69
70 if (!cms_DigestAlgorithm_find_ctx(mctx, chain, dd->digestAlgorithm))
71 goto err;
72
73 if (EVP_DigestFinal_ex(mctx, md, &mdlen) <= 0)
74 goto err;
75
76 if (verify) {
77 if (mdlen != (unsigned int)dd->digest->length) {
78 CMSerr(CMS_F_CMS_DIGESTEDDATA_DO_FINAL,
79 CMS_R_MESSAGEDIGEST_WRONG_LENGTH);
80 goto err;
81 }
82
83 if (memcmp(md, dd->digest->data, mdlen))
84 CMSerr(CMS_F_CMS_DIGESTEDDATA_DO_FINAL,
85 CMS_R_VERIFICATION_FAILURE);
86 else
87 r = 1;
88 } else {
89 if (!ASN1_STRING_set(dd->digest, md, mdlen))
90 goto err;
91 r = 1;
92 }
93
94 err:
95 EVP_MD_CTX_free(mctx);
96
97 return r;
98
99}
diff --git a/src/lib/libcrypto/cms/cms_enc.c b/src/lib/libcrypto/cms/cms_enc.c
new file mode 100644
index 0000000000..a1719830e8
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_enc.c
@@ -0,0 +1,213 @@
1/*
2 * Copyright 2008-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include <openssl/rand.h>
17#include "cms_lcl.h"
18
19/* CMS EncryptedData Utilities */
20
21/* Return BIO based on EncryptedContentInfo and key */
22
23BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec)
24{
25 BIO *b;
26 EVP_CIPHER_CTX *ctx;
27 const EVP_CIPHER *ciph;
28 X509_ALGOR *calg = ec->contentEncryptionAlgorithm;
29 unsigned char iv[EVP_MAX_IV_LENGTH], *piv = NULL;
30 unsigned char *tkey = NULL;
31 size_t tkeylen = 0;
32
33 int ok = 0;
34
35 int enc, keep_key = 0;
36
37 enc = ec->cipher ? 1 : 0;
38
39 b = BIO_new(BIO_f_cipher());
40 if (b == NULL) {
41 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, ERR_R_MALLOC_FAILURE);
42 return NULL;
43 }
44
45 BIO_get_cipher_ctx(b, &ctx);
46
47 if (enc) {
48 ciph = ec->cipher;
49 /*
50 * If not keeping key set cipher to NULL so subsequent calls decrypt.
51 */
52 if (ec->key)
53 ec->cipher = NULL;
54 } else {
55 ciph = EVP_get_cipherbyobj(calg->algorithm);
56
57 if (!ciph) {
58 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, CMS_R_UNKNOWN_CIPHER);
59 goto err;
60 }
61 }
62
63 if (EVP_CipherInit_ex(ctx, ciph, NULL, NULL, NULL, enc) <= 0) {
64 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
65 CMS_R_CIPHER_INITIALISATION_ERROR);
66 goto err;
67 }
68
69 if (enc) {
70 int ivlen;
71 calg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_type(ctx));
72 /* Generate a random IV if we need one */
73 ivlen = EVP_CIPHER_CTX_iv_length(ctx);
74 if (ivlen > 0) {
75 if (RAND_bytes(iv, ivlen) <= 0)
76 goto err;
77 piv = iv;
78 }
79 } else if (EVP_CIPHER_asn1_to_param(ctx, calg->parameter) <= 0) {
80 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
81 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
82 goto err;
83 }
84 tkeylen = EVP_CIPHER_CTX_key_length(ctx);
85 /* Generate random session key */
86 if (!enc || !ec->key) {
87 tkey = OPENSSL_malloc(tkeylen);
88 if (tkey == NULL) {
89 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, ERR_R_MALLOC_FAILURE);
90 goto err;
91 }
92 if (EVP_CIPHER_CTX_rand_key(ctx, tkey) <= 0)
93 goto err;
94 }
95
96 if (!ec->key) {
97 ec->key = tkey;
98 ec->keylen = tkeylen;
99 tkey = NULL;
100 if (enc)
101 keep_key = 1;
102 else
103 ERR_clear_error();
104
105 }
106
107 if (ec->keylen != tkeylen) {
108 /* If necessary set key length */
109 if (EVP_CIPHER_CTX_set_key_length(ctx, ec->keylen) <= 0) {
110 /*
111 * Only reveal failure if debugging so we don't leak information
112 * which may be useful in MMA.
113 */
114 if (enc || ec->debug) {
115 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
116 CMS_R_INVALID_KEY_LENGTH);
117 goto err;
118 } else {
119 /* Use random key */
120 OPENSSL_clear_free(ec->key, ec->keylen);
121 ec->key = tkey;
122 ec->keylen = tkeylen;
123 tkey = NULL;
124 ERR_clear_error();
125 }
126 }
127 }
128
129 if (EVP_CipherInit_ex(ctx, NULL, NULL, ec->key, piv, enc) <= 0) {
130 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
131 CMS_R_CIPHER_INITIALISATION_ERROR);
132 goto err;
133 }
134 if (enc) {
135 calg->parameter = ASN1_TYPE_new();
136 if (calg->parameter == NULL) {
137 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, ERR_R_MALLOC_FAILURE);
138 goto err;
139 }
140 if (EVP_CIPHER_param_to_asn1(ctx, calg->parameter) <= 0) {
141 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
142 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
143 goto err;
144 }
145 /* If parameter type not set omit parameter */
146 if (calg->parameter->type == V_ASN1_UNDEF) {
147 ASN1_TYPE_free(calg->parameter);
148 calg->parameter = NULL;
149 }
150 }
151 ok = 1;
152
153 err:
154 if (!keep_key || !ok) {
155 OPENSSL_clear_free(ec->key, ec->keylen);
156 ec->key = NULL;
157 }
158 OPENSSL_clear_free(tkey, tkeylen);
159 if (ok)
160 return b;
161 BIO_free(b);
162 return NULL;
163}
164
165int cms_EncryptedContent_init(CMS_EncryptedContentInfo *ec,
166 const EVP_CIPHER *cipher,
167 const unsigned char *key, size_t keylen)
168{
169 ec->cipher = cipher;
170 if (key) {
171 if ((ec->key = OPENSSL_malloc(keylen)) == NULL) {
172 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT, ERR_R_MALLOC_FAILURE);
173 return 0;
174 }
175 memcpy(ec->key, key, keylen);
176 }
177 ec->keylen = keylen;
178 if (cipher)
179 ec->contentType = OBJ_nid2obj(NID_pkcs7_data);
180 return 1;
181}
182
183int CMS_EncryptedData_set1_key(CMS_ContentInfo *cms, const EVP_CIPHER *ciph,
184 const unsigned char *key, size_t keylen)
185{
186 CMS_EncryptedContentInfo *ec;
187 if (!key || !keylen) {
188 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, CMS_R_NO_KEY);
189 return 0;
190 }
191 if (ciph) {
192 cms->d.encryptedData = M_ASN1_new_of(CMS_EncryptedData);
193 if (!cms->d.encryptedData) {
194 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, ERR_R_MALLOC_FAILURE);
195 return 0;
196 }
197 cms->contentType = OBJ_nid2obj(NID_pkcs7_encrypted);
198 cms->d.encryptedData->version = 0;
199 } else if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_encrypted) {
200 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, CMS_R_NOT_ENCRYPTED_DATA);
201 return 0;
202 }
203 ec = cms->d.encryptedData->encryptedContentInfo;
204 return cms_EncryptedContent_init(ec, ciph, key, keylen);
205}
206
207BIO *cms_EncryptedData_init_bio(CMS_ContentInfo *cms)
208{
209 CMS_EncryptedData *enc = cms->d.encryptedData;
210 if (enc->encryptedContentInfo->cipher && enc->unprotectedAttrs)
211 enc->version = 2;
212 return cms_EncryptedContent_init_bio(enc->encryptedContentInfo);
213}
diff --git a/src/lib/libcrypto/cms/cms_env.c b/src/lib/libcrypto/cms/cms_env.c
new file mode 100644
index 0000000000..bb95af75e3
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_env.c
@@ -0,0 +1,903 @@
1/*
2 * Copyright 2008-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include <openssl/aes.h>
17#include "cms_lcl.h"
18#include "internal/asn1_int.h"
19#include "internal/evp_int.h"
20
21/* CMS EnvelopedData Utilities */
22
23CMS_EnvelopedData *cms_get0_enveloped(CMS_ContentInfo *cms)
24{
25 if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_enveloped) {
26 CMSerr(CMS_F_CMS_GET0_ENVELOPED,
27 CMS_R_CONTENT_TYPE_NOT_ENVELOPED_DATA);
28 return NULL;
29 }
30 return cms->d.envelopedData;
31}
32
33static CMS_EnvelopedData *cms_enveloped_data_init(CMS_ContentInfo *cms)
34{
35 if (cms->d.other == NULL) {
36 cms->d.envelopedData = M_ASN1_new_of(CMS_EnvelopedData);
37 if (!cms->d.envelopedData) {
38 CMSerr(CMS_F_CMS_ENVELOPED_DATA_INIT, ERR_R_MALLOC_FAILURE);
39 return NULL;
40 }
41 cms->d.envelopedData->version = 0;
42 cms->d.envelopedData->encryptedContentInfo->contentType =
43 OBJ_nid2obj(NID_pkcs7_data);
44 ASN1_OBJECT_free(cms->contentType);
45 cms->contentType = OBJ_nid2obj(NID_pkcs7_enveloped);
46 return cms->d.envelopedData;
47 }
48 return cms_get0_enveloped(cms);
49}
50
51int cms_env_asn1_ctrl(CMS_RecipientInfo *ri, int cmd)
52{
53 EVP_PKEY *pkey;
54 int i;
55 if (ri->type == CMS_RECIPINFO_TRANS)
56 pkey = ri->d.ktri->pkey;
57 else if (ri->type == CMS_RECIPINFO_AGREE) {
58 EVP_PKEY_CTX *pctx = ri->d.kari->pctx;
59 if (!pctx)
60 return 0;
61 pkey = EVP_PKEY_CTX_get0_pkey(pctx);
62 if (!pkey)
63 return 0;
64 } else
65 return 0;
66 if (!pkey->ameth || !pkey->ameth->pkey_ctrl)
67 return 1;
68 i = pkey->ameth->pkey_ctrl(pkey, ASN1_PKEY_CTRL_CMS_ENVELOPE, cmd, ri);
69 if (i == -2) {
70 CMSerr(CMS_F_CMS_ENV_ASN1_CTRL,
71 CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
72 return 0;
73 }
74 if (i <= 0) {
75 CMSerr(CMS_F_CMS_ENV_ASN1_CTRL, CMS_R_CTRL_FAILURE);
76 return 0;
77 }
78 return 1;
79}
80
81STACK_OF(CMS_RecipientInfo) *CMS_get0_RecipientInfos(CMS_ContentInfo *cms)
82{
83 CMS_EnvelopedData *env;
84 env = cms_get0_enveloped(cms);
85 if (!env)
86 return NULL;
87 return env->recipientInfos;
88}
89
90int CMS_RecipientInfo_type(CMS_RecipientInfo *ri)
91{
92 return ri->type;
93}
94
95EVP_PKEY_CTX *CMS_RecipientInfo_get0_pkey_ctx(CMS_RecipientInfo *ri)
96{
97 if (ri->type == CMS_RECIPINFO_TRANS)
98 return ri->d.ktri->pctx;
99 else if (ri->type == CMS_RECIPINFO_AGREE)
100 return ri->d.kari->pctx;
101 return NULL;
102}
103
104CMS_ContentInfo *CMS_EnvelopedData_create(const EVP_CIPHER *cipher)
105{
106 CMS_ContentInfo *cms;
107 CMS_EnvelopedData *env;
108 cms = CMS_ContentInfo_new();
109 if (cms == NULL)
110 goto merr;
111 env = cms_enveloped_data_init(cms);
112 if (env == NULL)
113 goto merr;
114 if (!cms_EncryptedContent_init(env->encryptedContentInfo,
115 cipher, NULL, 0))
116 goto merr;
117 return cms;
118 merr:
119 CMS_ContentInfo_free(cms);
120 CMSerr(CMS_F_CMS_ENVELOPEDDATA_CREATE, ERR_R_MALLOC_FAILURE);
121 return NULL;
122}
123
124/* Key Transport Recipient Info (KTRI) routines */
125
126/* Initialise a ktri based on passed certificate and key */
127
128static int cms_RecipientInfo_ktri_init(CMS_RecipientInfo *ri, X509 *recip,
129 EVP_PKEY *pk, unsigned int flags)
130{
131 CMS_KeyTransRecipientInfo *ktri;
132 int idtype;
133
134 ri->d.ktri = M_ASN1_new_of(CMS_KeyTransRecipientInfo);
135 if (!ri->d.ktri)
136 return 0;
137 ri->type = CMS_RECIPINFO_TRANS;
138
139 ktri = ri->d.ktri;
140
141 if (flags & CMS_USE_KEYID) {
142 ktri->version = 2;
143 idtype = CMS_RECIPINFO_KEYIDENTIFIER;
144 } else {
145 ktri->version = 0;
146 idtype = CMS_RECIPINFO_ISSUER_SERIAL;
147 }
148
149 /*
150 * Not a typo: RecipientIdentifier and SignerIdentifier are the same
151 * structure.
152 */
153
154 if (!cms_set1_SignerIdentifier(ktri->rid, recip, idtype))
155 return 0;
156
157 X509_up_ref(recip);
158 EVP_PKEY_up_ref(pk);
159
160 ktri->pkey = pk;
161 ktri->recip = recip;
162
163 if (flags & CMS_KEY_PARAM) {
164 ktri->pctx = EVP_PKEY_CTX_new(ktri->pkey, NULL);
165 if (ktri->pctx == NULL)
166 return 0;
167 if (EVP_PKEY_encrypt_init(ktri->pctx) <= 0)
168 return 0;
169 } else if (!cms_env_asn1_ctrl(ri, 0))
170 return 0;
171 return 1;
172}
173
174/*
175 * Add a recipient certificate using appropriate type of RecipientInfo
176 */
177
178CMS_RecipientInfo *CMS_add1_recipient_cert(CMS_ContentInfo *cms,
179 X509 *recip, unsigned int flags)
180{
181 CMS_RecipientInfo *ri = NULL;
182 CMS_EnvelopedData *env;
183 EVP_PKEY *pk = NULL;
184 env = cms_get0_enveloped(cms);
185 if (!env)
186 goto err;
187
188 /* Initialize recipient info */
189 ri = M_ASN1_new_of(CMS_RecipientInfo);
190 if (!ri)
191 goto merr;
192
193 pk = X509_get0_pubkey(recip);
194 if (!pk) {
195 CMSerr(CMS_F_CMS_ADD1_RECIPIENT_CERT, CMS_R_ERROR_GETTING_PUBLIC_KEY);
196 goto err;
197 }
198
199 switch (cms_pkey_get_ri_type(pk)) {
200
201 case CMS_RECIPINFO_TRANS:
202 if (!cms_RecipientInfo_ktri_init(ri, recip, pk, flags))
203 goto err;
204 break;
205
206 case CMS_RECIPINFO_AGREE:
207 if (!cms_RecipientInfo_kari_init(ri, recip, pk, flags))
208 goto err;
209 break;
210
211 default:
212 CMSerr(CMS_F_CMS_ADD1_RECIPIENT_CERT,
213 CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
214 goto err;
215
216 }
217
218 if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri))
219 goto merr;
220
221 return ri;
222
223 merr:
224 CMSerr(CMS_F_CMS_ADD1_RECIPIENT_CERT, ERR_R_MALLOC_FAILURE);
225 err:
226 M_ASN1_free_of(ri, CMS_RecipientInfo);
227 return NULL;
228
229}
230
231int CMS_RecipientInfo_ktri_get0_algs(CMS_RecipientInfo *ri,
232 EVP_PKEY **pk, X509 **recip,
233 X509_ALGOR **palg)
234{
235 CMS_KeyTransRecipientInfo *ktri;
236 if (ri->type != CMS_RECIPINFO_TRANS) {
237 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_GET0_ALGS,
238 CMS_R_NOT_KEY_TRANSPORT);
239 return 0;
240 }
241
242 ktri = ri->d.ktri;
243
244 if (pk)
245 *pk = ktri->pkey;
246 if (recip)
247 *recip = ktri->recip;
248 if (palg)
249 *palg = ktri->keyEncryptionAlgorithm;
250 return 1;
251}
252
253int CMS_RecipientInfo_ktri_get0_signer_id(CMS_RecipientInfo *ri,
254 ASN1_OCTET_STRING **keyid,
255 X509_NAME **issuer,
256 ASN1_INTEGER **sno)
257{
258 CMS_KeyTransRecipientInfo *ktri;
259 if (ri->type != CMS_RECIPINFO_TRANS) {
260 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_GET0_SIGNER_ID,
261 CMS_R_NOT_KEY_TRANSPORT);
262 return 0;
263 }
264 ktri = ri->d.ktri;
265
266 return cms_SignerIdentifier_get0_signer_id(ktri->rid, keyid, issuer, sno);
267}
268
269int CMS_RecipientInfo_ktri_cert_cmp(CMS_RecipientInfo *ri, X509 *cert)
270{
271 if (ri->type != CMS_RECIPINFO_TRANS) {
272 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_CERT_CMP,
273 CMS_R_NOT_KEY_TRANSPORT);
274 return -2;
275 }
276 return cms_SignerIdentifier_cert_cmp(ri->d.ktri->rid, cert);
277}
278
279int CMS_RecipientInfo_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pkey)
280{
281 if (ri->type != CMS_RECIPINFO_TRANS) {
282 CMSerr(CMS_F_CMS_RECIPIENTINFO_SET0_PKEY, CMS_R_NOT_KEY_TRANSPORT);
283 return 0;
284 }
285 EVP_PKEY_free(ri->d.ktri->pkey);
286 ri->d.ktri->pkey = pkey;
287 return 1;
288}
289
290/* Encrypt content key in key transport recipient info */
291
292static int cms_RecipientInfo_ktri_encrypt(CMS_ContentInfo *cms,
293 CMS_RecipientInfo *ri)
294{
295 CMS_KeyTransRecipientInfo *ktri;
296 CMS_EncryptedContentInfo *ec;
297 EVP_PKEY_CTX *pctx;
298 unsigned char *ek = NULL;
299 size_t eklen;
300
301 int ret = 0;
302
303 if (ri->type != CMS_RECIPINFO_TRANS) {
304 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_ENCRYPT, CMS_R_NOT_KEY_TRANSPORT);
305 return 0;
306 }
307 ktri = ri->d.ktri;
308 ec = cms->d.envelopedData->encryptedContentInfo;
309
310 pctx = ktri->pctx;
311
312 if (pctx) {
313 if (!cms_env_asn1_ctrl(ri, 0))
314 goto err;
315 } else {
316 pctx = EVP_PKEY_CTX_new(ktri->pkey, NULL);
317 if (pctx == NULL)
318 return 0;
319
320 if (EVP_PKEY_encrypt_init(pctx) <= 0)
321 goto err;
322 }
323
324 if (EVP_PKEY_CTX_ctrl(pctx, -1, EVP_PKEY_OP_ENCRYPT,
325 EVP_PKEY_CTRL_CMS_ENCRYPT, 0, ri) <= 0) {
326 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_ENCRYPT, CMS_R_CTRL_ERROR);
327 goto err;
328 }
329
330 if (EVP_PKEY_encrypt(pctx, NULL, &eklen, ec->key, ec->keylen) <= 0)
331 goto err;
332
333 ek = OPENSSL_malloc(eklen);
334
335 if (ek == NULL) {
336 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_ENCRYPT, ERR_R_MALLOC_FAILURE);
337 goto err;
338 }
339
340 if (EVP_PKEY_encrypt(pctx, ek, &eklen, ec->key, ec->keylen) <= 0)
341 goto err;
342
343 ASN1_STRING_set0(ktri->encryptedKey, ek, eklen);
344 ek = NULL;
345
346 ret = 1;
347
348 err:
349 EVP_PKEY_CTX_free(pctx);
350 ktri->pctx = NULL;
351 OPENSSL_free(ek);
352 return ret;
353
354}
355
356/* Decrypt content key from KTRI */
357
358static int cms_RecipientInfo_ktri_decrypt(CMS_ContentInfo *cms,
359 CMS_RecipientInfo *ri)
360{
361 CMS_KeyTransRecipientInfo *ktri = ri->d.ktri;
362 EVP_PKEY *pkey = ktri->pkey;
363 unsigned char *ek = NULL;
364 size_t eklen;
365 int ret = 0;
366 CMS_EncryptedContentInfo *ec;
367 ec = cms->d.envelopedData->encryptedContentInfo;
368
369 if (ktri->pkey == NULL) {
370 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_DECRYPT, CMS_R_NO_PRIVATE_KEY);
371 return 0;
372 }
373
374 ktri->pctx = EVP_PKEY_CTX_new(pkey, NULL);
375 if (ktri->pctx == NULL)
376 return 0;
377
378 if (EVP_PKEY_decrypt_init(ktri->pctx) <= 0)
379 goto err;
380
381 if (!cms_env_asn1_ctrl(ri, 1))
382 goto err;
383
384 if (EVP_PKEY_CTX_ctrl(ktri->pctx, -1, EVP_PKEY_OP_DECRYPT,
385 EVP_PKEY_CTRL_CMS_DECRYPT, 0, ri) <= 0) {
386 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_DECRYPT, CMS_R_CTRL_ERROR);
387 goto err;
388 }
389
390 if (EVP_PKEY_decrypt(ktri->pctx, NULL, &eklen,
391 ktri->encryptedKey->data,
392 ktri->encryptedKey->length) <= 0)
393 goto err;
394
395 ek = OPENSSL_malloc(eklen);
396
397 if (ek == NULL) {
398 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_DECRYPT, ERR_R_MALLOC_FAILURE);
399 goto err;
400 }
401
402 if (EVP_PKEY_decrypt(ktri->pctx, ek, &eklen,
403 ktri->encryptedKey->data,
404 ktri->encryptedKey->length) <= 0) {
405 CMSerr(CMS_F_CMS_RECIPIENTINFO_KTRI_DECRYPT, CMS_R_CMS_LIB);
406 goto err;
407 }
408
409 ret = 1;
410
411 OPENSSL_clear_free(ec->key, ec->keylen);
412 ec->key = ek;
413 ec->keylen = eklen;
414
415 err:
416 EVP_PKEY_CTX_free(ktri->pctx);
417 ktri->pctx = NULL;
418 if (!ret)
419 OPENSSL_free(ek);
420
421 return ret;
422}
423
424/* Key Encrypted Key (KEK) RecipientInfo routines */
425
426int CMS_RecipientInfo_kekri_id_cmp(CMS_RecipientInfo *ri,
427 const unsigned char *id, size_t idlen)
428{
429 ASN1_OCTET_STRING tmp_os;
430 CMS_KEKRecipientInfo *kekri;
431 if (ri->type != CMS_RECIPINFO_KEK) {
432 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_ID_CMP, CMS_R_NOT_KEK);
433 return -2;
434 }
435 kekri = ri->d.kekri;
436 tmp_os.type = V_ASN1_OCTET_STRING;
437 tmp_os.flags = 0;
438 tmp_os.data = (unsigned char *)id;
439 tmp_os.length = (int)idlen;
440 return ASN1_OCTET_STRING_cmp(&tmp_os, kekri->kekid->keyIdentifier);
441}
442
443/* For now hard code AES key wrap info */
444
445static size_t aes_wrap_keylen(int nid)
446{
447 switch (nid) {
448 case NID_id_aes128_wrap:
449 return 16;
450
451 case NID_id_aes192_wrap:
452 return 24;
453
454 case NID_id_aes256_wrap:
455 return 32;
456
457 default:
458 return 0;
459 }
460}
461
462CMS_RecipientInfo *CMS_add0_recipient_key(CMS_ContentInfo *cms, int nid,
463 unsigned char *key, size_t keylen,
464 unsigned char *id, size_t idlen,
465 ASN1_GENERALIZEDTIME *date,
466 ASN1_OBJECT *otherTypeId,
467 ASN1_TYPE *otherType)
468{
469 CMS_RecipientInfo *ri = NULL;
470 CMS_EnvelopedData *env;
471 CMS_KEKRecipientInfo *kekri;
472 env = cms_get0_enveloped(cms);
473 if (!env)
474 goto err;
475
476 if (nid == NID_undef) {
477 switch (keylen) {
478 case 16:
479 nid = NID_id_aes128_wrap;
480 break;
481
482 case 24:
483 nid = NID_id_aes192_wrap;
484 break;
485
486 case 32:
487 nid = NID_id_aes256_wrap;
488 break;
489
490 default:
491 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_KEY, CMS_R_INVALID_KEY_LENGTH);
492 goto err;
493 }
494
495 } else {
496
497 size_t exp_keylen = aes_wrap_keylen(nid);
498
499 if (!exp_keylen) {
500 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_KEY,
501 CMS_R_UNSUPPORTED_KEK_ALGORITHM);
502 goto err;
503 }
504
505 if (keylen != exp_keylen) {
506 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_KEY, CMS_R_INVALID_KEY_LENGTH);
507 goto err;
508 }
509
510 }
511
512 /* Initialize recipient info */
513 ri = M_ASN1_new_of(CMS_RecipientInfo);
514 if (!ri)
515 goto merr;
516
517 ri->d.kekri = M_ASN1_new_of(CMS_KEKRecipientInfo);
518 if (!ri->d.kekri)
519 goto merr;
520 ri->type = CMS_RECIPINFO_KEK;
521
522 kekri = ri->d.kekri;
523
524 if (otherTypeId) {
525 kekri->kekid->other = M_ASN1_new_of(CMS_OtherKeyAttribute);
526 if (kekri->kekid->other == NULL)
527 goto merr;
528 }
529
530 if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri))
531 goto merr;
532
533 /* After this point no calls can fail */
534
535 kekri->version = 4;
536
537 kekri->key = key;
538 kekri->keylen = keylen;
539
540 ASN1_STRING_set0(kekri->kekid->keyIdentifier, id, idlen);
541
542 kekri->kekid->date = date;
543
544 if (kekri->kekid->other) {
545 kekri->kekid->other->keyAttrId = otherTypeId;
546 kekri->kekid->other->keyAttr = otherType;
547 }
548
549 X509_ALGOR_set0(kekri->keyEncryptionAlgorithm,
550 OBJ_nid2obj(nid), V_ASN1_UNDEF, NULL);
551
552 return ri;
553
554 merr:
555 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_KEY, ERR_R_MALLOC_FAILURE);
556 err:
557 M_ASN1_free_of(ri, CMS_RecipientInfo);
558 return NULL;
559
560}
561
562int CMS_RecipientInfo_kekri_get0_id(CMS_RecipientInfo *ri,
563 X509_ALGOR **palg,
564 ASN1_OCTET_STRING **pid,
565 ASN1_GENERALIZEDTIME **pdate,
566 ASN1_OBJECT **potherid,
567 ASN1_TYPE **pothertype)
568{
569 CMS_KEKIdentifier *rkid;
570 if (ri->type != CMS_RECIPINFO_KEK) {
571 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID, CMS_R_NOT_KEK);
572 return 0;
573 }
574 rkid = ri->d.kekri->kekid;
575 if (palg)
576 *palg = ri->d.kekri->keyEncryptionAlgorithm;
577 if (pid)
578 *pid = rkid->keyIdentifier;
579 if (pdate)
580 *pdate = rkid->date;
581 if (potherid) {
582 if (rkid->other)
583 *potherid = rkid->other->keyAttrId;
584 else
585 *potherid = NULL;
586 }
587 if (pothertype) {
588 if (rkid->other)
589 *pothertype = rkid->other->keyAttr;
590 else
591 *pothertype = NULL;
592 }
593 return 1;
594}
595
596int CMS_RecipientInfo_set0_key(CMS_RecipientInfo *ri,
597 unsigned char *key, size_t keylen)
598{
599 CMS_KEKRecipientInfo *kekri;
600 if (ri->type != CMS_RECIPINFO_KEK) {
601 CMSerr(CMS_F_CMS_RECIPIENTINFO_SET0_KEY, CMS_R_NOT_KEK);
602 return 0;
603 }
604
605 kekri = ri->d.kekri;
606 kekri->key = key;
607 kekri->keylen = keylen;
608 return 1;
609}
610
611/* Encrypt content key in KEK recipient info */
612
613static int cms_RecipientInfo_kekri_encrypt(CMS_ContentInfo *cms,
614 CMS_RecipientInfo *ri)
615{
616 CMS_EncryptedContentInfo *ec;
617 CMS_KEKRecipientInfo *kekri;
618 AES_KEY actx;
619 unsigned char *wkey = NULL;
620 int wkeylen;
621 int r = 0;
622
623 ec = cms->d.envelopedData->encryptedContentInfo;
624
625 kekri = ri->d.kekri;
626
627 if (!kekri->key) {
628 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT, CMS_R_NO_KEY);
629 return 0;
630 }
631
632 if (AES_set_encrypt_key(kekri->key, kekri->keylen << 3, &actx)) {
633 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT,
634 CMS_R_ERROR_SETTING_KEY);
635 goto err;
636 }
637
638 wkey = OPENSSL_malloc(ec->keylen + 8);
639
640 if (wkey == NULL) {
641 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT, ERR_R_MALLOC_FAILURE);
642 goto err;
643 }
644
645 wkeylen = AES_wrap_key(&actx, NULL, wkey, ec->key, ec->keylen);
646
647 if (wkeylen <= 0) {
648 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT, CMS_R_WRAP_ERROR);
649 goto err;
650 }
651
652 ASN1_STRING_set0(kekri->encryptedKey, wkey, wkeylen);
653
654 r = 1;
655
656 err:
657
658 if (!r)
659 OPENSSL_free(wkey);
660 OPENSSL_cleanse(&actx, sizeof(actx));
661
662 return r;
663
664}
665
666/* Decrypt content key in KEK recipient info */
667
668static int cms_RecipientInfo_kekri_decrypt(CMS_ContentInfo *cms,
669 CMS_RecipientInfo *ri)
670{
671 CMS_EncryptedContentInfo *ec;
672 CMS_KEKRecipientInfo *kekri;
673 AES_KEY actx;
674 unsigned char *ukey = NULL;
675 int ukeylen;
676 int r = 0, wrap_nid;
677
678 ec = cms->d.envelopedData->encryptedContentInfo;
679
680 kekri = ri->d.kekri;
681
682 if (!kekri->key) {
683 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT, CMS_R_NO_KEY);
684 return 0;
685 }
686
687 wrap_nid = OBJ_obj2nid(kekri->keyEncryptionAlgorithm->algorithm);
688 if (aes_wrap_keylen(wrap_nid) != kekri->keylen) {
689 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT,
690 CMS_R_INVALID_KEY_LENGTH);
691 return 0;
692 }
693
694 /* If encrypted key length is invalid don't bother */
695
696 if (kekri->encryptedKey->length < 16) {
697 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT,
698 CMS_R_INVALID_ENCRYPTED_KEY_LENGTH);
699 goto err;
700 }
701
702 if (AES_set_decrypt_key(kekri->key, kekri->keylen << 3, &actx)) {
703 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT,
704 CMS_R_ERROR_SETTING_KEY);
705 goto err;
706 }
707
708 ukey = OPENSSL_malloc(kekri->encryptedKey->length - 8);
709
710 if (ukey == NULL) {
711 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT, ERR_R_MALLOC_FAILURE);
712 goto err;
713 }
714
715 ukeylen = AES_unwrap_key(&actx, NULL, ukey,
716 kekri->encryptedKey->data,
717 kekri->encryptedKey->length);
718
719 if (ukeylen <= 0) {
720 CMSerr(CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT, CMS_R_UNWRAP_ERROR);
721 goto err;
722 }
723
724 ec->key = ukey;
725 ec->keylen = ukeylen;
726
727 r = 1;
728
729 err:
730
731 if (!r)
732 OPENSSL_free(ukey);
733 OPENSSL_cleanse(&actx, sizeof(actx));
734
735 return r;
736
737}
738
739int CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
740{
741 switch (ri->type) {
742 case CMS_RECIPINFO_TRANS:
743 return cms_RecipientInfo_ktri_decrypt(cms, ri);
744
745 case CMS_RECIPINFO_KEK:
746 return cms_RecipientInfo_kekri_decrypt(cms, ri);
747
748 case CMS_RECIPINFO_PASS:
749 return cms_RecipientInfo_pwri_crypt(cms, ri, 0);
750
751 default:
752 CMSerr(CMS_F_CMS_RECIPIENTINFO_DECRYPT,
753 CMS_R_UNSUPPORTED_RECIPIENTINFO_TYPE);
754 return 0;
755 }
756}
757
758int CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
759{
760 switch (ri->type) {
761 case CMS_RECIPINFO_TRANS:
762 return cms_RecipientInfo_ktri_encrypt(cms, ri);
763
764 case CMS_RECIPINFO_AGREE:
765 return cms_RecipientInfo_kari_encrypt(cms, ri);
766
767 case CMS_RECIPINFO_KEK:
768 return cms_RecipientInfo_kekri_encrypt(cms, ri);
769
770 case CMS_RECIPINFO_PASS:
771 return cms_RecipientInfo_pwri_crypt(cms, ri, 1);
772
773 default:
774 CMSerr(CMS_F_CMS_RECIPIENTINFO_ENCRYPT,
775 CMS_R_UNSUPPORTED_RECIPIENT_TYPE);
776 return 0;
777 }
778}
779
780/* Check structures and fixup version numbers (if necessary) */
781
782static void cms_env_set_originfo_version(CMS_EnvelopedData *env)
783{
784 CMS_OriginatorInfo *org = env->originatorInfo;
785 int i;
786 if (org == NULL)
787 return;
788 for (i = 0; i < sk_CMS_CertificateChoices_num(org->certificates); i++) {
789 CMS_CertificateChoices *cch;
790 cch = sk_CMS_CertificateChoices_value(org->certificates, i);
791 if (cch->type == CMS_CERTCHOICE_OTHER) {
792 env->version = 4;
793 return;
794 } else if (cch->type == CMS_CERTCHOICE_V2ACERT) {
795 if (env->version < 3)
796 env->version = 3;
797 }
798 }
799
800 for (i = 0; i < sk_CMS_RevocationInfoChoice_num(org->crls); i++) {
801 CMS_RevocationInfoChoice *rch;
802 rch = sk_CMS_RevocationInfoChoice_value(org->crls, i);
803 if (rch->type == CMS_REVCHOICE_OTHER) {
804 env->version = 4;
805 return;
806 }
807 }
808}
809
810static void cms_env_set_version(CMS_EnvelopedData *env)
811{
812 int i;
813 CMS_RecipientInfo *ri;
814
815 /*
816 * Can't set version higher than 4 so if 4 or more already nothing to do.
817 */
818 if (env->version >= 4)
819 return;
820
821 cms_env_set_originfo_version(env);
822
823 if (env->version >= 3)
824 return;
825
826 for (i = 0; i < sk_CMS_RecipientInfo_num(env->recipientInfos); i++) {
827 ri = sk_CMS_RecipientInfo_value(env->recipientInfos, i);
828 if (ri->type == CMS_RECIPINFO_PASS || ri->type == CMS_RECIPINFO_OTHER) {
829 env->version = 3;
830 return;
831 } else if (ri->type != CMS_RECIPINFO_TRANS
832 || ri->d.ktri->version != 0) {
833 env->version = 2;
834 }
835 }
836 if (env->originatorInfo || env->unprotectedAttrs)
837 env->version = 2;
838 if (env->version == 2)
839 return;
840 env->version = 0;
841}
842
843BIO *cms_EnvelopedData_init_bio(CMS_ContentInfo *cms)
844{
845 CMS_EncryptedContentInfo *ec;
846 STACK_OF(CMS_RecipientInfo) *rinfos;
847 CMS_RecipientInfo *ri;
848 int i, ok = 0;
849 BIO *ret;
850
851 /* Get BIO first to set up key */
852
853 ec = cms->d.envelopedData->encryptedContentInfo;
854 ret = cms_EncryptedContent_init_bio(ec);
855
856 /* If error or no cipher end of processing */
857
858 if (!ret || !ec->cipher)
859 return ret;
860
861 /* Now encrypt content key according to each RecipientInfo type */
862
863 rinfos = cms->d.envelopedData->recipientInfos;
864
865 for (i = 0; i < sk_CMS_RecipientInfo_num(rinfos); i++) {
866 ri = sk_CMS_RecipientInfo_value(rinfos, i);
867 if (CMS_RecipientInfo_encrypt(cms, ri) <= 0) {
868 CMSerr(CMS_F_CMS_ENVELOPEDDATA_INIT_BIO,
869 CMS_R_ERROR_SETTING_RECIPIENTINFO);
870 goto err;
871 }
872 }
873 cms_env_set_version(cms->d.envelopedData);
874
875 ok = 1;
876
877 err:
878 ec->cipher = NULL;
879 OPENSSL_clear_free(ec->key, ec->keylen);
880 ec->key = NULL;
881 ec->keylen = 0;
882 if (ok)
883 return ret;
884 BIO_free(ret);
885 return NULL;
886
887}
888
889/*
890 * Get RecipientInfo type (if any) supported by a key (public or private). To
891 * retain compatibility with previous behaviour if the ctrl value isn't
892 * supported we assume key transport.
893 */
894int cms_pkey_get_ri_type(EVP_PKEY *pk)
895{
896 if (pk->ameth && pk->ameth->pkey_ctrl) {
897 int i, r;
898 i = pk->ameth->pkey_ctrl(pk, ASN1_PKEY_CTRL_CMS_RI_TYPE, 0, &r);
899 if (i > 0)
900 return r;
901 }
902 return CMS_RECIPINFO_TRANS;
903}
diff --git a/src/lib/libcrypto/cms/cms_err.c b/src/lib/libcrypto/cms/cms_err.c
new file mode 100644
index 0000000000..4432b471ee
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_err.c
@@ -0,0 +1,294 @@
1/*
2 * Generated by util/mkerr.pl DO NOT EDIT
3 * Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
4 *
5 * Licensed under the OpenSSL license (the "License"). You may not use
6 * this file except in compliance with the License. You can obtain a copy
7 * in the file LICENSE in the source distribution or at
8 * https://www.openssl.org/source/license.html
9 */
10
11#include <openssl/err.h>
12#include <openssl/cmserr.h>
13
14#ifndef OPENSSL_NO_ERR
15
16static const ERR_STRING_DATA CMS_str_functs[] = {
17 {ERR_PACK(ERR_LIB_CMS, CMS_F_CHECK_CONTENT, 0), "check_content"},
18 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD0_CERT, 0), "CMS_add0_cert"},
19 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD0_RECIPIENT_KEY, 0),
20 "CMS_add0_recipient_key"},
21 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, 0),
22 "CMS_add0_recipient_password"},
23 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD1_RECEIPTREQUEST, 0),
24 "CMS_add1_ReceiptRequest"},
25 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD1_RECIPIENT_CERT, 0),
26 "CMS_add1_recipient_cert"},
27 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD1_SIGNER, 0), "CMS_add1_signer"},
28 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ADD1_SIGNINGTIME, 0),
29 "cms_add1_signingTime"},
30 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_COMPRESS, 0), "CMS_compress"},
31 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_COMPRESSEDDATA_CREATE, 0),
32 "cms_CompressedData_create"},
33 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_COMPRESSEDDATA_INIT_BIO, 0),
34 "cms_CompressedData_init_bio"},
35 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_COPY_CONTENT, 0), "cms_copy_content"},
36 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_COPY_MESSAGEDIGEST, 0),
37 "cms_copy_messageDigest"},
38 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DATA, 0), "CMS_data"},
39 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DATAFINAL, 0), "CMS_dataFinal"},
40 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DATAINIT, 0), "CMS_dataInit"},
41 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DECRYPT, 0), "CMS_decrypt"},
42 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DECRYPT_SET1_KEY, 0),
43 "CMS_decrypt_set1_key"},
44 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DECRYPT_SET1_PASSWORD, 0),
45 "CMS_decrypt_set1_password"},
46 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DECRYPT_SET1_PKEY, 0),
47 "CMS_decrypt_set1_pkey"},
48 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DIGESTALGORITHM_FIND_CTX, 0),
49 "cms_DigestAlgorithm_find_ctx"},
50 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DIGESTALGORITHM_INIT_BIO, 0),
51 "cms_DigestAlgorithm_init_bio"},
52 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DIGESTEDDATA_DO_FINAL, 0),
53 "cms_DigestedData_do_final"},
54 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_DIGEST_VERIFY, 0), "CMS_digest_verify"},
55 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCODE_RECEIPT, 0), "cms_encode_Receipt"},
56 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPT, 0), "CMS_encrypt"},
57 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPTEDCONTENT_INIT, 0),
58 "cms_EncryptedContent_init"},
59 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 0),
60 "cms_EncryptedContent_init_bio"},
61 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPTEDDATA_DECRYPT, 0),
62 "CMS_EncryptedData_decrypt"},
63 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPTEDDATA_ENCRYPT, 0),
64 "CMS_EncryptedData_encrypt"},
65 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, 0),
66 "CMS_EncryptedData_set1_key"},
67 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENVELOPEDDATA_CREATE, 0),
68 "CMS_EnvelopedData_create"},
69 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENVELOPEDDATA_INIT_BIO, 0),
70 "cms_EnvelopedData_init_bio"},
71 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENVELOPED_DATA_INIT, 0),
72 "cms_enveloped_data_init"},
73 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_ENV_ASN1_CTRL, 0), "cms_env_asn1_ctrl"},
74 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_FINAL, 0), "CMS_final"},
75 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_CERTIFICATE_CHOICES, 0),
76 "cms_get0_certificate_choices"},
77 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_CONTENT, 0), "CMS_get0_content"},
78 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_ECONTENT_TYPE, 0),
79 "cms_get0_econtent_type"},
80 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_ENVELOPED, 0), "cms_get0_enveloped"},
81 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_REVOCATION_CHOICES, 0),
82 "cms_get0_revocation_choices"},
83 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_GET0_SIGNED, 0), "cms_get0_signed"},
84 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_MSGSIGDIGEST_ADD1, 0),
85 "cms_msgSigDigest_add1"},
86 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECEIPTREQUEST_CREATE0, 0),
87 "CMS_ReceiptRequest_create0"},
88 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECEIPT_VERIFY, 0), "cms_Receipt_verify"},
89 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_DECRYPT, 0),
90 "CMS_RecipientInfo_decrypt"},
91 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_ENCRYPT, 0),
92 "CMS_RecipientInfo_encrypt"},
93 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KARI_ENCRYPT, 0),
94 "cms_RecipientInfo_kari_encrypt"},
95 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KARI_GET0_ALG, 0),
96 "CMS_RecipientInfo_kari_get0_alg"},
97 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KARI_GET0_ORIG_ID, 0),
98 "CMS_RecipientInfo_kari_get0_orig_id"},
99 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KARI_GET0_REKS, 0),
100 "CMS_RecipientInfo_kari_get0_reks"},
101 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KARI_ORIG_ID_CMP, 0),
102 "CMS_RecipientInfo_kari_orig_id_cmp"},
103 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KEKRI_DECRYPT, 0),
104 "cms_RecipientInfo_kekri_decrypt"},
105 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KEKRI_ENCRYPT, 0),
106 "cms_RecipientInfo_kekri_encrypt"},
107 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KEKRI_GET0_ID, 0),
108 "CMS_RecipientInfo_kekri_get0_id"},
109 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KEKRI_ID_CMP, 0),
110 "CMS_RecipientInfo_kekri_id_cmp"},
111 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KTRI_CERT_CMP, 0),
112 "CMS_RecipientInfo_ktri_cert_cmp"},
113 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KTRI_DECRYPT, 0),
114 "cms_RecipientInfo_ktri_decrypt"},
115 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KTRI_ENCRYPT, 0),
116 "cms_RecipientInfo_ktri_encrypt"},
117 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KTRI_GET0_ALGS, 0),
118 "CMS_RecipientInfo_ktri_get0_algs"},
119 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_KTRI_GET0_SIGNER_ID, 0),
120 "CMS_RecipientInfo_ktri_get0_signer_id"},
121 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, 0),
122 "cms_RecipientInfo_pwri_crypt"},
123 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_SET0_KEY, 0),
124 "CMS_RecipientInfo_set0_key"},
125 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_SET0_PASSWORD, 0),
126 "CMS_RecipientInfo_set0_password"},
127 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_RECIPIENTINFO_SET0_PKEY, 0),
128 "CMS_RecipientInfo_set0_pkey"},
129 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SD_ASN1_CTRL, 0), "cms_sd_asn1_ctrl"},
130 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SET1_IAS, 0), "cms_set1_ias"},
131 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SET1_KEYID, 0), "cms_set1_keyid"},
132 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SET1_SIGNERIDENTIFIER, 0),
133 "cms_set1_SignerIdentifier"},
134 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SET_DETACHED, 0), "CMS_set_detached"},
135 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGN, 0), "CMS_sign"},
136 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNED_DATA_INIT, 0),
137 "cms_signed_data_init"},
138 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, 0),
139 "cms_SignerInfo_content_sign"},
140 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNERINFO_SIGN, 0),
141 "CMS_SignerInfo_sign"},
142 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNERINFO_VERIFY, 0),
143 "CMS_SignerInfo_verify"},
144 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNERINFO_VERIFY_CERT, 0),
145 "cms_signerinfo_verify_cert"},
146 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT, 0),
147 "CMS_SignerInfo_verify_content"},
148 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_SIGN_RECEIPT, 0), "CMS_sign_receipt"},
149 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_STREAM, 0), "CMS_stream"},
150 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_UNCOMPRESS, 0), "CMS_uncompress"},
151 {ERR_PACK(ERR_LIB_CMS, CMS_F_CMS_VERIFY, 0), "CMS_verify"},
152 {ERR_PACK(ERR_LIB_CMS, CMS_F_KEK_UNWRAP_KEY, 0), "kek_unwrap_key"},
153 {0, NULL}
154};
155
156static const ERR_STRING_DATA CMS_str_reasons[] = {
157 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_ADD_SIGNER_ERROR), "add signer error"},
158 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CERTIFICATE_ALREADY_PRESENT),
159 "certificate already present"},
160 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CERTIFICATE_HAS_NO_KEYID),
161 "certificate has no keyid"},
162 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CERTIFICATE_VERIFY_ERROR),
163 "certificate verify error"},
164 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CIPHER_INITIALISATION_ERROR),
165 "cipher initialisation error"},
166 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR),
167 "cipher parameter initialisation error"},
168 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CMS_DATAFINAL_ERROR),
169 "cms datafinal error"},
170 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CMS_LIB), "cms lib"},
171 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENTIDENTIFIER_MISMATCH),
172 "contentidentifier mismatch"},
173 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_NOT_FOUND), "content not found"},
174 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_TYPE_MISMATCH),
175 "content type mismatch"},
176 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_TYPE_NOT_COMPRESSED_DATA),
177 "content type not compressed data"},
178 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_TYPE_NOT_ENVELOPED_DATA),
179 "content type not enveloped data"},
180 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_TYPE_NOT_SIGNED_DATA),
181 "content type not signed data"},
182 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CONTENT_VERIFY_ERROR),
183 "content verify error"},
184 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CTRL_ERROR), "ctrl error"},
185 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_CTRL_FAILURE), "ctrl failure"},
186 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_DECRYPT_ERROR), "decrypt error"},
187 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_ERROR_GETTING_PUBLIC_KEY),
188 "error getting public key"},
189 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_ERROR_READING_MESSAGEDIGEST_ATTRIBUTE),
190 "error reading messagedigest attribute"},
191 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_ERROR_SETTING_KEY), "error setting key"},
192 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_ERROR_SETTING_RECIPIENTINFO),
193 "error setting recipientinfo"},
194 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_INVALID_ENCRYPTED_KEY_LENGTH),
195 "invalid encrypted key length"},
196 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_INVALID_KEY_ENCRYPTION_PARAMETER),
197 "invalid key encryption parameter"},
198 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_INVALID_KEY_LENGTH), "invalid key length"},
199 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MD_BIO_INIT_ERROR), "md bio init error"},
200 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MESSAGEDIGEST_ATTRIBUTE_WRONG_LENGTH),
201 "messagedigest attribute wrong length"},
202 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MESSAGEDIGEST_WRONG_LENGTH),
203 "messagedigest wrong length"},
204 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MSGSIGDIGEST_ERROR), "msgsigdigest error"},
205 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MSGSIGDIGEST_VERIFICATION_FAILURE),
206 "msgsigdigest verification failure"},
207 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_MSGSIGDIGEST_WRONG_LENGTH),
208 "msgsigdigest wrong length"},
209 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NEED_ONE_SIGNER), "need one signer"},
210 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_A_SIGNED_RECEIPT),
211 "not a signed receipt"},
212 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_ENCRYPTED_DATA), "not encrypted data"},
213 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEK), "not kek"},
214 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEY_AGREEMENT), "not key agreement"},
215 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_KEY_TRANSPORT), "not key transport"},
216 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_PWRI), "not pwri"},
217 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE),
218 "not supported for this key type"},
219 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_CIPHER), "no cipher"},
220 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_CONTENT), "no content"},
221 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_CONTENT_TYPE), "no content type"},
222 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_DEFAULT_DIGEST), "no default digest"},
223 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_DIGEST_SET), "no digest set"},
224 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_KEY), "no key"},
225 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_KEY_OR_CERT), "no key or cert"},
226 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_MATCHING_DIGEST), "no matching digest"},
227 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_MATCHING_RECIPIENT),
228 "no matching recipient"},
229 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_MATCHING_SIGNATURE),
230 "no matching signature"},
231 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_MSGSIGDIGEST), "no msgsigdigest"},
232 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_PASSWORD), "no password"},
233 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_PRIVATE_KEY), "no private key"},
234 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_PUBLIC_KEY), "no public key"},
235 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_RECEIPT_REQUEST), "no receipt request"},
236 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_NO_SIGNERS), "no signers"},
237 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_PRIVATE_KEY_DOES_NOT_MATCH_CERTIFICATE),
238 "private key does not match certificate"},
239 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_RECEIPT_DECODE_ERROR),
240 "receipt decode error"},
241 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_RECIPIENT_ERROR), "recipient error"},
242 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_SIGNER_CERTIFICATE_NOT_FOUND),
243 "signer certificate not found"},
244 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_SIGNFINAL_ERROR), "signfinal error"},
245 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_SMIME_TEXT_ERROR), "smime text error"},
246 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_STORE_INIT_ERROR), "store init error"},
247 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_TYPE_NOT_COMPRESSED_DATA),
248 "type not compressed data"},
249 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_TYPE_NOT_DATA), "type not data"},
250 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_TYPE_NOT_DIGESTED_DATA),
251 "type not digested data"},
252 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_TYPE_NOT_ENCRYPTED_DATA),
253 "type not encrypted data"},
254 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_TYPE_NOT_ENVELOPED_DATA),
255 "type not enveloped data"},
256 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNABLE_TO_FINALIZE_CONTEXT),
257 "unable to finalize context"},
258 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_CIPHER), "unknown cipher"},
259 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_DIGEST_ALGORITHM),
260 "unknown digest algorithm"},
261 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNKNOWN_ID), "unknown id"},
262 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM),
263 "unsupported compression algorithm"},
264 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_CONTENT_TYPE),
265 "unsupported content type"},
266 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_KEK_ALGORITHM),
267 "unsupported kek algorithm"},
268 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM),
269 "unsupported key encryption algorithm"},
270 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_RECIPIENTINFO_TYPE),
271 "unsupported recipientinfo type"},
272 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_RECIPIENT_TYPE),
273 "unsupported recipient type"},
274 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNSUPPORTED_TYPE), "unsupported type"},
275 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNWRAP_ERROR), "unwrap error"},
276 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_UNWRAP_FAILURE), "unwrap failure"},
277 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_VERIFICATION_FAILURE),
278 "verification failure"},
279 {ERR_PACK(ERR_LIB_CMS, 0, CMS_R_WRAP_ERROR), "wrap error"},
280 {0, NULL}
281};
282
283#endif
284
285int ERR_load_CMS_strings(void)
286{
287#ifndef OPENSSL_NO_ERR
288 if (ERR_func_error_string(CMS_str_functs[0].error) == NULL) {
289 ERR_load_strings_const(CMS_str_functs);
290 ERR_load_strings_const(CMS_str_reasons);
291 }
292#endif
293 return 1;
294}
diff --git a/src/lib/libcrypto/cms/cms_ess.c b/src/lib/libcrypto/cms/cms_ess.c
new file mode 100644
index 0000000000..4780231c22
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_ess.c
@@ -0,0 +1,337 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/rand.h>
14#include <openssl/x509v3.h>
15#include <openssl/err.h>
16#include <openssl/cms.h>
17#include "cms_lcl.h"
18
19IMPLEMENT_ASN1_FUNCTIONS(CMS_ReceiptRequest)
20
21/* ESS services: for now just Signed Receipt related */
22
23int CMS_get1_ReceiptRequest(CMS_SignerInfo *si, CMS_ReceiptRequest **prr)
24{
25 ASN1_STRING *str;
26 CMS_ReceiptRequest *rr = NULL;
27 if (prr)
28 *prr = NULL;
29 str = CMS_signed_get0_data_by_OBJ(si,
30 OBJ_nid2obj
31 (NID_id_smime_aa_receiptRequest), -3,
32 V_ASN1_SEQUENCE);
33 if (!str)
34 return 0;
35
36 rr = ASN1_item_unpack(str, ASN1_ITEM_rptr(CMS_ReceiptRequest));
37 if (!rr)
38 return -1;
39 if (prr)
40 *prr = rr;
41 else
42 CMS_ReceiptRequest_free(rr);
43 return 1;
44}
45
46CMS_ReceiptRequest *CMS_ReceiptRequest_create0(unsigned char *id, int idlen,
47 int allorfirst,
48 STACK_OF(GENERAL_NAMES)
49 *receiptList, STACK_OF(GENERAL_NAMES)
50 *receiptsTo)
51{
52 CMS_ReceiptRequest *rr = NULL;
53
54 rr = CMS_ReceiptRequest_new();
55 if (rr == NULL)
56 goto merr;
57 if (id)
58 ASN1_STRING_set0(rr->signedContentIdentifier, id, idlen);
59 else {
60 if (!ASN1_STRING_set(rr->signedContentIdentifier, NULL, 32))
61 goto merr;
62 if (RAND_bytes(rr->signedContentIdentifier->data, 32) <= 0)
63 goto err;
64 }
65
66 sk_GENERAL_NAMES_pop_free(rr->receiptsTo, GENERAL_NAMES_free);
67 rr->receiptsTo = receiptsTo;
68
69 if (receiptList) {
70 rr->receiptsFrom->type = 1;
71 rr->receiptsFrom->d.receiptList = receiptList;
72 } else {
73 rr->receiptsFrom->type = 0;
74 rr->receiptsFrom->d.allOrFirstTier = allorfirst;
75 }
76
77 return rr;
78
79 merr:
80 CMSerr(CMS_F_CMS_RECEIPTREQUEST_CREATE0, ERR_R_MALLOC_FAILURE);
81
82 err:
83 CMS_ReceiptRequest_free(rr);
84 return NULL;
85
86}
87
88int CMS_add1_ReceiptRequest(CMS_SignerInfo *si, CMS_ReceiptRequest *rr)
89{
90 unsigned char *rrder = NULL;
91 int rrderlen, r = 0;
92
93 rrderlen = i2d_CMS_ReceiptRequest(rr, &rrder);
94 if (rrderlen < 0)
95 goto merr;
96
97 if (!CMS_signed_add1_attr_by_NID(si, NID_id_smime_aa_receiptRequest,
98 V_ASN1_SEQUENCE, rrder, rrderlen))
99 goto merr;
100
101 r = 1;
102
103 merr:
104 if (!r)
105 CMSerr(CMS_F_CMS_ADD1_RECEIPTREQUEST, ERR_R_MALLOC_FAILURE);
106
107 OPENSSL_free(rrder);
108
109 return r;
110
111}
112
113void CMS_ReceiptRequest_get0_values(CMS_ReceiptRequest *rr,
114 ASN1_STRING **pcid,
115 int *pallorfirst,
116 STACK_OF(GENERAL_NAMES) **plist,
117 STACK_OF(GENERAL_NAMES) **prto)
118{
119 if (pcid)
120 *pcid = rr->signedContentIdentifier;
121 if (rr->receiptsFrom->type == 0) {
122 if (pallorfirst)
123 *pallorfirst = (int)rr->receiptsFrom->d.allOrFirstTier;
124 if (plist)
125 *plist = NULL;
126 } else {
127 if (pallorfirst)
128 *pallorfirst = -1;
129 if (plist)
130 *plist = rr->receiptsFrom->d.receiptList;
131 }
132 if (prto)
133 *prto = rr->receiptsTo;
134}
135
136/* Digest a SignerInfo structure for msgSigDigest attribute processing */
137
138static int cms_msgSigDigest(CMS_SignerInfo *si,
139 unsigned char *dig, unsigned int *diglen)
140{
141 const EVP_MD *md;
142 md = EVP_get_digestbyobj(si->digestAlgorithm->algorithm);
143 if (md == NULL)
144 return 0;
145 if (!ASN1_item_digest(ASN1_ITEM_rptr(CMS_Attributes_Verify), md,
146 si->signedAttrs, dig, diglen))
147 return 0;
148 return 1;
149}
150
151/* Add a msgSigDigest attribute to a SignerInfo */
152
153int cms_msgSigDigest_add1(CMS_SignerInfo *dest, CMS_SignerInfo *src)
154{
155 unsigned char dig[EVP_MAX_MD_SIZE];
156 unsigned int diglen;
157 if (!cms_msgSigDigest(src, dig, &diglen)) {
158 CMSerr(CMS_F_CMS_MSGSIGDIGEST_ADD1, CMS_R_MSGSIGDIGEST_ERROR);
159 return 0;
160 }
161 if (!CMS_signed_add1_attr_by_NID(dest, NID_id_smime_aa_msgSigDigest,
162 V_ASN1_OCTET_STRING, dig, diglen)) {
163 CMSerr(CMS_F_CMS_MSGSIGDIGEST_ADD1, ERR_R_MALLOC_FAILURE);
164 return 0;
165 }
166 return 1;
167}
168
169/* Verify signed receipt after it has already passed normal CMS verify */
170
171int cms_Receipt_verify(CMS_ContentInfo *cms, CMS_ContentInfo *req_cms)
172{
173 int r = 0, i;
174 CMS_ReceiptRequest *rr = NULL;
175 CMS_Receipt *rct = NULL;
176 STACK_OF(CMS_SignerInfo) *sis, *osis;
177 CMS_SignerInfo *si, *osi = NULL;
178 ASN1_OCTET_STRING *msig, **pcont;
179 ASN1_OBJECT *octype;
180 unsigned char dig[EVP_MAX_MD_SIZE];
181 unsigned int diglen;
182
183 /* Get SignerInfos, also checks SignedData content type */
184 osis = CMS_get0_SignerInfos(req_cms);
185 sis = CMS_get0_SignerInfos(cms);
186 if (!osis || !sis)
187 goto err;
188
189 if (sk_CMS_SignerInfo_num(sis) != 1) {
190 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NEED_ONE_SIGNER);
191 goto err;
192 }
193
194 /* Check receipt content type */
195 if (OBJ_obj2nid(CMS_get0_eContentType(cms)) != NID_id_smime_ct_receipt) {
196 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NOT_A_SIGNED_RECEIPT);
197 goto err;
198 }
199
200 /* Extract and decode receipt content */
201 pcont = CMS_get0_content(cms);
202 if (!pcont || !*pcont) {
203 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NO_CONTENT);
204 goto err;
205 }
206
207 rct = ASN1_item_unpack(*pcont, ASN1_ITEM_rptr(CMS_Receipt));
208
209 if (!rct) {
210 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_RECEIPT_DECODE_ERROR);
211 goto err;
212 }
213
214 /* Locate original request */
215
216 for (i = 0; i < sk_CMS_SignerInfo_num(osis); i++) {
217 osi = sk_CMS_SignerInfo_value(osis, i);
218 if (!ASN1_STRING_cmp(osi->signature, rct->originatorSignatureValue))
219 break;
220 }
221
222 if (i == sk_CMS_SignerInfo_num(osis)) {
223 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NO_MATCHING_SIGNATURE);
224 goto err;
225 }
226
227 si = sk_CMS_SignerInfo_value(sis, 0);
228
229 /* Get msgSigDigest value and compare */
230
231 msig = CMS_signed_get0_data_by_OBJ(si,
232 OBJ_nid2obj
233 (NID_id_smime_aa_msgSigDigest), -3,
234 V_ASN1_OCTET_STRING);
235
236 if (!msig) {
237 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NO_MSGSIGDIGEST);
238 goto err;
239 }
240
241 if (!cms_msgSigDigest(osi, dig, &diglen)) {
242 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_MSGSIGDIGEST_ERROR);
243 goto err;
244 }
245
246 if (diglen != (unsigned int)msig->length) {
247 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_MSGSIGDIGEST_WRONG_LENGTH);
248 goto err;
249 }
250
251 if (memcmp(dig, msig->data, diglen)) {
252 CMSerr(CMS_F_CMS_RECEIPT_VERIFY,
253 CMS_R_MSGSIGDIGEST_VERIFICATION_FAILURE);
254 goto err;
255 }
256
257 /* Compare content types */
258
259 octype = CMS_signed_get0_data_by_OBJ(osi,
260 OBJ_nid2obj(NID_pkcs9_contentType),
261 -3, V_ASN1_OBJECT);
262 if (!octype) {
263 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NO_CONTENT_TYPE);
264 goto err;
265 }
266
267 /* Compare details in receipt request */
268
269 if (OBJ_cmp(octype, rct->contentType)) {
270 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_CONTENT_TYPE_MISMATCH);
271 goto err;
272 }
273
274 /* Get original receipt request details */
275
276 if (CMS_get1_ReceiptRequest(osi, &rr) <= 0) {
277 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_NO_RECEIPT_REQUEST);
278 goto err;
279 }
280
281 if (ASN1_STRING_cmp(rr->signedContentIdentifier,
282 rct->signedContentIdentifier)) {
283 CMSerr(CMS_F_CMS_RECEIPT_VERIFY, CMS_R_CONTENTIDENTIFIER_MISMATCH);
284 goto err;
285 }
286
287 r = 1;
288
289 err:
290 CMS_ReceiptRequest_free(rr);
291 M_ASN1_free_of(rct, CMS_Receipt);
292 return r;
293
294}
295
296/*
297 * Encode a Receipt into an OCTET STRING read for including into content of a
298 * SignedData ContentInfo.
299 */
300
301ASN1_OCTET_STRING *cms_encode_Receipt(CMS_SignerInfo *si)
302{
303 CMS_Receipt rct;
304 CMS_ReceiptRequest *rr = NULL;
305 ASN1_OBJECT *ctype;
306 ASN1_OCTET_STRING *os = NULL;
307
308 /* Get original receipt request */
309
310 /* Get original receipt request details */
311
312 if (CMS_get1_ReceiptRequest(si, &rr) <= 0) {
313 CMSerr(CMS_F_CMS_ENCODE_RECEIPT, CMS_R_NO_RECEIPT_REQUEST);
314 goto err;
315 }
316
317 /* Get original content type */
318
319 ctype = CMS_signed_get0_data_by_OBJ(si,
320 OBJ_nid2obj(NID_pkcs9_contentType),
321 -3, V_ASN1_OBJECT);
322 if (!ctype) {
323 CMSerr(CMS_F_CMS_ENCODE_RECEIPT, CMS_R_NO_CONTENT_TYPE);
324 goto err;
325 }
326
327 rct.version = 1;
328 rct.contentType = ctype;
329 rct.signedContentIdentifier = rr->signedContentIdentifier;
330 rct.originatorSignatureValue = si->signature;
331
332 os = ASN1_item_pack(&rct, ASN1_ITEM_rptr(CMS_Receipt), NULL);
333
334 err:
335 CMS_ReceiptRequest_free(rr);
336 return os;
337}
diff --git a/src/lib/libcrypto/cms/cms_io.c b/src/lib/libcrypto/cms/cms_io.c
new file mode 100644
index 0000000000..d18f980a97
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_io.c
@@ -0,0 +1,88 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include <openssl/asn1t.h>
11#include <openssl/x509.h>
12#include <openssl/err.h>
13#include <openssl/pem.h>
14#include <openssl/cms.h>
15#include "cms_lcl.h"
16
17int CMS_stream(unsigned char ***boundary, CMS_ContentInfo *cms)
18{
19 ASN1_OCTET_STRING **pos;
20 pos = CMS_get0_content(cms);
21 if (pos == NULL)
22 return 0;
23 if (*pos == NULL)
24 *pos = ASN1_OCTET_STRING_new();
25 if (*pos != NULL) {
26 (*pos)->flags |= ASN1_STRING_FLAG_NDEF;
27 (*pos)->flags &= ~ASN1_STRING_FLAG_CONT;
28 *boundary = &(*pos)->data;
29 return 1;
30 }
31 CMSerr(CMS_F_CMS_STREAM, ERR_R_MALLOC_FAILURE);
32 return 0;
33}
34
35CMS_ContentInfo *d2i_CMS_bio(BIO *bp, CMS_ContentInfo **cms)
36{
37 return ASN1_item_d2i_bio(ASN1_ITEM_rptr(CMS_ContentInfo), bp, cms);
38}
39
40int i2d_CMS_bio(BIO *bp, CMS_ContentInfo *cms)
41{
42 return ASN1_item_i2d_bio(ASN1_ITEM_rptr(CMS_ContentInfo), bp, cms);
43}
44
45IMPLEMENT_PEM_rw_const(CMS, CMS_ContentInfo, PEM_STRING_CMS, CMS_ContentInfo)
46
47BIO *BIO_new_CMS(BIO *out, CMS_ContentInfo *cms)
48{
49 return BIO_new_NDEF(out, (ASN1_VALUE *)cms,
50 ASN1_ITEM_rptr(CMS_ContentInfo));
51}
52
53/* CMS wrappers round generalised stream and MIME routines */
54
55int i2d_CMS_bio_stream(BIO *out, CMS_ContentInfo *cms, BIO *in, int flags)
56{
57 return i2d_ASN1_bio_stream(out, (ASN1_VALUE *)cms, in, flags,
58 ASN1_ITEM_rptr(CMS_ContentInfo));
59}
60
61int PEM_write_bio_CMS_stream(BIO *out, CMS_ContentInfo *cms, BIO *in,
62 int flags)
63{
64 return PEM_write_bio_ASN1_stream(out, (ASN1_VALUE *)cms, in, flags,
65 "CMS", ASN1_ITEM_rptr(CMS_ContentInfo));
66}
67
68int SMIME_write_CMS(BIO *bio, CMS_ContentInfo *cms, BIO *data, int flags)
69{
70 STACK_OF(X509_ALGOR) *mdalgs;
71 int ctype_nid = OBJ_obj2nid(cms->contentType);
72 int econt_nid = OBJ_obj2nid(CMS_get0_eContentType(cms));
73 if (ctype_nid == NID_pkcs7_signed)
74 mdalgs = cms->d.signedData->digestAlgorithms;
75 else
76 mdalgs = NULL;
77
78 return SMIME_write_ASN1(bio, (ASN1_VALUE *)cms, data, flags,
79 ctype_nid, econt_nid, mdalgs,
80 ASN1_ITEM_rptr(CMS_ContentInfo));
81}
82
83CMS_ContentInfo *SMIME_read_CMS(BIO *bio, BIO **bcont)
84{
85 return (CMS_ContentInfo *)SMIME_read_ASN1(bio, bcont,
86 ASN1_ITEM_rptr
87 (CMS_ContentInfo));
88}
diff --git a/src/lib/libcrypto/cms/cms_kari.c b/src/lib/libcrypto/cms/cms_kari.c
new file mode 100644
index 0000000000..5e83814d0f
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_kari.c
@@ -0,0 +1,414 @@
1/*
2 * Copyright 2013-2019 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include <openssl/aes.h>
17#include "cms_lcl.h"
18#include "internal/asn1_int.h"
19
20/* Key Agreement Recipient Info (KARI) routines */
21
22int CMS_RecipientInfo_kari_get0_alg(CMS_RecipientInfo *ri,
23 X509_ALGOR **palg,
24 ASN1_OCTET_STRING **pukm)
25{
26 if (ri->type != CMS_RECIPINFO_AGREE) {
27 CMSerr(CMS_F_CMS_RECIPIENTINFO_KARI_GET0_ALG,
28 CMS_R_NOT_KEY_AGREEMENT);
29 return 0;
30 }
31 if (palg)
32 *palg = ri->d.kari->keyEncryptionAlgorithm;
33 if (pukm)
34 *pukm = ri->d.kari->ukm;
35 return 1;
36}
37
38/* Retrieve recipient encrypted keys from a kari */
39
40STACK_OF(CMS_RecipientEncryptedKey)
41*CMS_RecipientInfo_kari_get0_reks(CMS_RecipientInfo *ri)
42{
43 if (ri->type != CMS_RECIPINFO_AGREE) {
44 CMSerr(CMS_F_CMS_RECIPIENTINFO_KARI_GET0_REKS,
45 CMS_R_NOT_KEY_AGREEMENT);
46 return NULL;
47 }
48 return ri->d.kari->recipientEncryptedKeys;
49}
50
51int CMS_RecipientInfo_kari_get0_orig_id(CMS_RecipientInfo *ri,
52 X509_ALGOR **pubalg,
53 ASN1_BIT_STRING **pubkey,
54 ASN1_OCTET_STRING **keyid,
55 X509_NAME **issuer,
56 ASN1_INTEGER **sno)
57{
58 CMS_OriginatorIdentifierOrKey *oik;
59 if (ri->type != CMS_RECIPINFO_AGREE) {
60 CMSerr(CMS_F_CMS_RECIPIENTINFO_KARI_GET0_ORIG_ID,
61 CMS_R_NOT_KEY_AGREEMENT);
62 return 0;
63 }
64 oik = ri->d.kari->originator;
65 if (issuer)
66 *issuer = NULL;
67 if (sno)
68 *sno = NULL;
69 if (keyid)
70 *keyid = NULL;
71 if (pubalg)
72 *pubalg = NULL;
73 if (pubkey)
74 *pubkey = NULL;
75 if (oik->type == CMS_OIK_ISSUER_SERIAL) {
76 if (issuer)
77 *issuer = oik->d.issuerAndSerialNumber->issuer;
78 if (sno)
79 *sno = oik->d.issuerAndSerialNumber->serialNumber;
80 } else if (oik->type == CMS_OIK_KEYIDENTIFIER) {
81 if (keyid)
82 *keyid = oik->d.subjectKeyIdentifier;
83 } else if (oik->type == CMS_OIK_PUBKEY) {
84 if (pubalg)
85 *pubalg = oik->d.originatorKey->algorithm;
86 if (pubkey)
87 *pubkey = oik->d.originatorKey->publicKey;
88 } else
89 return 0;
90 return 1;
91}
92
93int CMS_RecipientInfo_kari_orig_id_cmp(CMS_RecipientInfo *ri, X509 *cert)
94{
95 CMS_OriginatorIdentifierOrKey *oik;
96 if (ri->type != CMS_RECIPINFO_AGREE) {
97 CMSerr(CMS_F_CMS_RECIPIENTINFO_KARI_ORIG_ID_CMP,
98 CMS_R_NOT_KEY_AGREEMENT);
99 return -2;
100 }
101 oik = ri->d.kari->originator;
102 if (oik->type == CMS_OIK_ISSUER_SERIAL)
103 return cms_ias_cert_cmp(oik->d.issuerAndSerialNumber, cert);
104 else if (oik->type == CMS_OIK_KEYIDENTIFIER)
105 return cms_keyid_cert_cmp(oik->d.subjectKeyIdentifier, cert);
106 return -1;
107}
108
109int CMS_RecipientEncryptedKey_get0_id(CMS_RecipientEncryptedKey *rek,
110 ASN1_OCTET_STRING **keyid,
111 ASN1_GENERALIZEDTIME **tm,
112 CMS_OtherKeyAttribute **other,
113 X509_NAME **issuer, ASN1_INTEGER **sno)
114{
115 CMS_KeyAgreeRecipientIdentifier *rid = rek->rid;
116 if (rid->type == CMS_REK_ISSUER_SERIAL) {
117 if (issuer)
118 *issuer = rid->d.issuerAndSerialNumber->issuer;
119 if (sno)
120 *sno = rid->d.issuerAndSerialNumber->serialNumber;
121 if (keyid)
122 *keyid = NULL;
123 if (tm)
124 *tm = NULL;
125 if (other)
126 *other = NULL;
127 } else if (rid->type == CMS_REK_KEYIDENTIFIER) {
128 if (keyid)
129 *keyid = rid->d.rKeyId->subjectKeyIdentifier;
130 if (tm)
131 *tm = rid->d.rKeyId->date;
132 if (other)
133 *other = rid->d.rKeyId->other;
134 if (issuer)
135 *issuer = NULL;
136 if (sno)
137 *sno = NULL;
138 } else
139 return 0;
140 return 1;
141}
142
143int CMS_RecipientEncryptedKey_cert_cmp(CMS_RecipientEncryptedKey *rek,
144 X509 *cert)
145{
146 CMS_KeyAgreeRecipientIdentifier *rid = rek->rid;
147 if (rid->type == CMS_REK_ISSUER_SERIAL)
148 return cms_ias_cert_cmp(rid->d.issuerAndSerialNumber, cert);
149 else if (rid->type == CMS_REK_KEYIDENTIFIER)
150 return cms_keyid_cert_cmp(rid->d.rKeyId->subjectKeyIdentifier, cert);
151 else
152 return -1;
153}
154
155int CMS_RecipientInfo_kari_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pk)
156{
157 EVP_PKEY_CTX *pctx;
158 CMS_KeyAgreeRecipientInfo *kari = ri->d.kari;
159
160 EVP_PKEY_CTX_free(kari->pctx);
161 kari->pctx = NULL;
162 if (!pk)
163 return 1;
164 pctx = EVP_PKEY_CTX_new(pk, NULL);
165 if (!pctx || !EVP_PKEY_derive_init(pctx))
166 goto err;
167 kari->pctx = pctx;
168 return 1;
169 err:
170 EVP_PKEY_CTX_free(pctx);
171 return 0;
172}
173
174EVP_CIPHER_CTX *CMS_RecipientInfo_kari_get0_ctx(CMS_RecipientInfo *ri)
175{
176 if (ri->type == CMS_RECIPINFO_AGREE)
177 return ri->d.kari->ctx;
178 return NULL;
179}
180
181/*
182 * Derive KEK and decrypt/encrypt with it to produce either the original CEK
183 * or the encrypted CEK.
184 */
185
186static int cms_kek_cipher(unsigned char **pout, size_t *poutlen,
187 const unsigned char *in, size_t inlen,
188 CMS_KeyAgreeRecipientInfo *kari, int enc)
189{
190 /* Key encryption key */
191 unsigned char kek[EVP_MAX_KEY_LENGTH];
192 size_t keklen;
193 int rv = 0;
194 unsigned char *out = NULL;
195 int outlen;
196 keklen = EVP_CIPHER_CTX_key_length(kari->ctx);
197 if (keklen > EVP_MAX_KEY_LENGTH)
198 return 0;
199 /* Derive KEK */
200 if (EVP_PKEY_derive(kari->pctx, kek, &keklen) <= 0)
201 goto err;
202 /* Set KEK in context */
203 if (!EVP_CipherInit_ex(kari->ctx, NULL, NULL, kek, NULL, enc))
204 goto err;
205 /* obtain output length of ciphered key */
206 if (!EVP_CipherUpdate(kari->ctx, NULL, &outlen, in, inlen))
207 goto err;
208 out = OPENSSL_malloc(outlen);
209 if (out == NULL)
210 goto err;
211 if (!EVP_CipherUpdate(kari->ctx, out, &outlen, in, inlen))
212 goto err;
213 *pout = out;
214 *poutlen = (size_t)outlen;
215 rv = 1;
216
217 err:
218 OPENSSL_cleanse(kek, keklen);
219 if (!rv)
220 OPENSSL_free(out);
221 EVP_CIPHER_CTX_reset(kari->ctx);
222 /* FIXME: WHY IS kari->pctx freed here? /RL */
223 EVP_PKEY_CTX_free(kari->pctx);
224 kari->pctx = NULL;
225 return rv;
226}
227
228int CMS_RecipientInfo_kari_decrypt(CMS_ContentInfo *cms,
229 CMS_RecipientInfo *ri,
230 CMS_RecipientEncryptedKey *rek)
231{
232 int rv = 0;
233 unsigned char *enckey = NULL, *cek = NULL;
234 size_t enckeylen;
235 size_t ceklen;
236 CMS_EncryptedContentInfo *ec;
237 enckeylen = rek->encryptedKey->length;
238 enckey = rek->encryptedKey->data;
239 /* Setup all parameters to derive KEK */
240 if (!cms_env_asn1_ctrl(ri, 1))
241 goto err;
242 /* Attempt to decrypt CEK */
243 if (!cms_kek_cipher(&cek, &ceklen, enckey, enckeylen, ri->d.kari, 0))
244 goto err;
245 ec = cms->d.envelopedData->encryptedContentInfo;
246 OPENSSL_clear_free(ec->key, ec->keylen);
247 ec->key = cek;
248 ec->keylen = ceklen;
249 cek = NULL;
250 rv = 1;
251 err:
252 OPENSSL_free(cek);
253 return rv;
254}
255
256/* Create ephemeral key and initialise context based on it */
257static int cms_kari_create_ephemeral_key(CMS_KeyAgreeRecipientInfo *kari,
258 EVP_PKEY *pk)
259{
260 EVP_PKEY_CTX *pctx = NULL;
261 EVP_PKEY *ekey = NULL;
262 int rv = 0;
263 pctx = EVP_PKEY_CTX_new(pk, NULL);
264 if (!pctx)
265 goto err;
266 if (EVP_PKEY_keygen_init(pctx) <= 0)
267 goto err;
268 if (EVP_PKEY_keygen(pctx, &ekey) <= 0)
269 goto err;
270 EVP_PKEY_CTX_free(pctx);
271 pctx = EVP_PKEY_CTX_new(ekey, NULL);
272 if (!pctx)
273 goto err;
274 if (EVP_PKEY_derive_init(pctx) <= 0)
275 goto err;
276 kari->pctx = pctx;
277 rv = 1;
278 err:
279 if (!rv)
280 EVP_PKEY_CTX_free(pctx);
281 EVP_PKEY_free(ekey);
282 return rv;
283}
284
285/* Initialise a kari based on passed certificate and key */
286
287int cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
288 EVP_PKEY *pk, unsigned int flags)
289{
290 CMS_KeyAgreeRecipientInfo *kari;
291 CMS_RecipientEncryptedKey *rek = NULL;
292
293 ri->d.kari = M_ASN1_new_of(CMS_KeyAgreeRecipientInfo);
294 if (!ri->d.kari)
295 return 0;
296 ri->type = CMS_RECIPINFO_AGREE;
297
298 kari = ri->d.kari;
299 kari->version = 3;
300
301 rek = M_ASN1_new_of(CMS_RecipientEncryptedKey);
302 if (rek == NULL)
303 return 0;
304
305 if (!sk_CMS_RecipientEncryptedKey_push(kari->recipientEncryptedKeys, rek)) {
306 M_ASN1_free_of(rek, CMS_RecipientEncryptedKey);
307 return 0;
308 }
309
310 if (flags & CMS_USE_KEYID) {
311 rek->rid->type = CMS_REK_KEYIDENTIFIER;
312 rek->rid->d.rKeyId = M_ASN1_new_of(CMS_RecipientKeyIdentifier);
313 if (rek->rid->d.rKeyId == NULL)
314 return 0;
315 if (!cms_set1_keyid(&rek->rid->d.rKeyId->subjectKeyIdentifier, recip))
316 return 0;
317 } else {
318 rek->rid->type = CMS_REK_ISSUER_SERIAL;
319 if (!cms_set1_ias(&rek->rid->d.issuerAndSerialNumber, recip))
320 return 0;
321 }
322
323 /* Create ephemeral key */
324 if (!cms_kari_create_ephemeral_key(kari, pk))
325 return 0;
326
327 EVP_PKEY_up_ref(pk);
328 rek->pkey = pk;
329 return 1;
330}
331
332static int cms_wrap_init(CMS_KeyAgreeRecipientInfo *kari,
333 const EVP_CIPHER *cipher)
334{
335 EVP_CIPHER_CTX *ctx = kari->ctx;
336 const EVP_CIPHER *kekcipher;
337 int keylen = EVP_CIPHER_key_length(cipher);
338 /* If a suitable wrap algorithm is already set nothing to do */
339 kekcipher = EVP_CIPHER_CTX_cipher(ctx);
340
341 if (kekcipher) {
342 if (EVP_CIPHER_CTX_mode(ctx) != EVP_CIPH_WRAP_MODE)
343 return 0;
344 return 1;
345 }
346 /*
347 * Pick a cipher based on content encryption cipher. If it is DES3 use
348 * DES3 wrap otherwise use AES wrap similar to key size.
349 */
350#ifndef OPENSSL_NO_DES
351 if (EVP_CIPHER_type(cipher) == NID_des_ede3_cbc)
352 kekcipher = EVP_des_ede3_wrap();
353 else
354#endif
355 if (keylen <= 16)
356 kekcipher = EVP_aes_128_wrap();
357 else if (keylen <= 24)
358 kekcipher = EVP_aes_192_wrap();
359 else
360 kekcipher = EVP_aes_256_wrap();
361 return EVP_EncryptInit_ex(ctx, kekcipher, NULL, NULL, NULL);
362}
363
364/* Encrypt content key in key agreement recipient info */
365
366int cms_RecipientInfo_kari_encrypt(CMS_ContentInfo *cms,
367 CMS_RecipientInfo *ri)
368{
369 CMS_KeyAgreeRecipientInfo *kari;
370 CMS_EncryptedContentInfo *ec;
371 CMS_RecipientEncryptedKey *rek;
372 STACK_OF(CMS_RecipientEncryptedKey) *reks;
373 int i;
374
375 if (ri->type != CMS_RECIPINFO_AGREE) {
376 CMSerr(CMS_F_CMS_RECIPIENTINFO_KARI_ENCRYPT, CMS_R_NOT_KEY_AGREEMENT);
377 return 0;
378 }
379 kari = ri->d.kari;
380 reks = kari->recipientEncryptedKeys;
381 ec = cms->d.envelopedData->encryptedContentInfo;
382 /* Initialise wrap algorithm parameters */
383 if (!cms_wrap_init(kari, ec->cipher))
384 return 0;
385 /*
386 * If no originator key set up initialise for ephemeral key the public key
387 * ASN1 structure will set the actual public key value.
388 */
389 if (kari->originator->type == -1) {
390 CMS_OriginatorIdentifierOrKey *oik = kari->originator;
391 oik->type = CMS_OIK_PUBKEY;
392 oik->d.originatorKey = M_ASN1_new_of(CMS_OriginatorPublicKey);
393 if (!oik->d.originatorKey)
394 return 0;
395 }
396 /* Initialise KDF algorithm */
397 if (!cms_env_asn1_ctrl(ri, 0))
398 return 0;
399 /* For each rek, derive KEK, encrypt CEK */
400 for (i = 0; i < sk_CMS_RecipientEncryptedKey_num(reks); i++) {
401 unsigned char *enckey;
402 size_t enckeylen;
403 rek = sk_CMS_RecipientEncryptedKey_value(reks, i);
404 if (EVP_PKEY_derive_set_peer(kari->pctx, rek->pkey) <= 0)
405 return 0;
406 if (!cms_kek_cipher(&enckey, &enckeylen, ec->key, ec->keylen,
407 kari, 1))
408 return 0;
409 ASN1_STRING_set0(rek->encryptedKey, enckey, enckeylen);
410 }
411
412 return 1;
413
414}
diff --git a/src/lib/libcrypto/cms/cms_lcl.h b/src/lib/libcrypto/cms/cms_lcl.h
new file mode 100644
index 0000000000..916fcbfbe1
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_lcl.h
@@ -0,0 +1,437 @@
1/*
2 * Copyright 2008-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#ifndef HEADER_CMS_LCL_H
11# define HEADER_CMS_LCL_H
12
13# include <openssl/x509.h>
14
15/*
16 * Cryptographic message syntax (CMS) structures: taken from RFC3852
17 */
18
19/* Forward references */
20
21typedef struct CMS_IssuerAndSerialNumber_st CMS_IssuerAndSerialNumber;
22typedef struct CMS_EncapsulatedContentInfo_st CMS_EncapsulatedContentInfo;
23typedef struct CMS_SignerIdentifier_st CMS_SignerIdentifier;
24typedef struct CMS_SignedData_st CMS_SignedData;
25typedef struct CMS_OtherRevocationInfoFormat_st CMS_OtherRevocationInfoFormat;
26typedef struct CMS_OriginatorInfo_st CMS_OriginatorInfo;
27typedef struct CMS_EncryptedContentInfo_st CMS_EncryptedContentInfo;
28typedef struct CMS_EnvelopedData_st CMS_EnvelopedData;
29typedef struct CMS_DigestedData_st CMS_DigestedData;
30typedef struct CMS_EncryptedData_st CMS_EncryptedData;
31typedef struct CMS_AuthenticatedData_st CMS_AuthenticatedData;
32typedef struct CMS_CompressedData_st CMS_CompressedData;
33typedef struct CMS_OtherCertificateFormat_st CMS_OtherCertificateFormat;
34typedef struct CMS_KeyTransRecipientInfo_st CMS_KeyTransRecipientInfo;
35typedef struct CMS_OriginatorPublicKey_st CMS_OriginatorPublicKey;
36typedef struct CMS_OriginatorIdentifierOrKey_st CMS_OriginatorIdentifierOrKey;
37typedef struct CMS_KeyAgreeRecipientInfo_st CMS_KeyAgreeRecipientInfo;
38typedef struct CMS_RecipientKeyIdentifier_st CMS_RecipientKeyIdentifier;
39typedef struct CMS_KeyAgreeRecipientIdentifier_st
40 CMS_KeyAgreeRecipientIdentifier;
41typedef struct CMS_KEKIdentifier_st CMS_KEKIdentifier;
42typedef struct CMS_KEKRecipientInfo_st CMS_KEKRecipientInfo;
43typedef struct CMS_PasswordRecipientInfo_st CMS_PasswordRecipientInfo;
44typedef struct CMS_OtherRecipientInfo_st CMS_OtherRecipientInfo;
45typedef struct CMS_ReceiptsFrom_st CMS_ReceiptsFrom;
46
47struct CMS_ContentInfo_st {
48 ASN1_OBJECT *contentType;
49 union {
50 ASN1_OCTET_STRING *data;
51 CMS_SignedData *signedData;
52 CMS_EnvelopedData *envelopedData;
53 CMS_DigestedData *digestedData;
54 CMS_EncryptedData *encryptedData;
55 CMS_AuthenticatedData *authenticatedData;
56 CMS_CompressedData *compressedData;
57 ASN1_TYPE *other;
58 /* Other types ... */
59 void *otherData;
60 } d;
61};
62
63DEFINE_STACK_OF(CMS_CertificateChoices)
64
65struct CMS_SignedData_st {
66 int32_t version;
67 STACK_OF(X509_ALGOR) *digestAlgorithms;
68 CMS_EncapsulatedContentInfo *encapContentInfo;
69 STACK_OF(CMS_CertificateChoices) *certificates;
70 STACK_OF(CMS_RevocationInfoChoice) *crls;
71 STACK_OF(CMS_SignerInfo) *signerInfos;
72};
73
74struct CMS_EncapsulatedContentInfo_st {
75 ASN1_OBJECT *eContentType;
76 ASN1_OCTET_STRING *eContent;
77 /* Set to 1 if incomplete structure only part set up */
78 int partial;
79};
80
81struct CMS_SignerInfo_st {
82 int32_t version;
83 CMS_SignerIdentifier *sid;
84 X509_ALGOR *digestAlgorithm;
85 STACK_OF(X509_ATTRIBUTE) *signedAttrs;
86 X509_ALGOR *signatureAlgorithm;
87 ASN1_OCTET_STRING *signature;
88 STACK_OF(X509_ATTRIBUTE) *unsignedAttrs;
89 /* Signing certificate and key */
90 X509 *signer;
91 EVP_PKEY *pkey;
92 /* Digest and public key context for alternative parameters */
93 EVP_MD_CTX *mctx;
94 EVP_PKEY_CTX *pctx;
95};
96
97struct CMS_SignerIdentifier_st {
98 int type;
99 union {
100 CMS_IssuerAndSerialNumber *issuerAndSerialNumber;
101 ASN1_OCTET_STRING *subjectKeyIdentifier;
102 } d;
103};
104
105struct CMS_EnvelopedData_st {
106 int32_t version;
107 CMS_OriginatorInfo *originatorInfo;
108 STACK_OF(CMS_RecipientInfo) *recipientInfos;
109 CMS_EncryptedContentInfo *encryptedContentInfo;
110 STACK_OF(X509_ATTRIBUTE) *unprotectedAttrs;
111};
112
113struct CMS_OriginatorInfo_st {
114 STACK_OF(CMS_CertificateChoices) *certificates;
115 STACK_OF(CMS_RevocationInfoChoice) *crls;
116};
117
118struct CMS_EncryptedContentInfo_st {
119 ASN1_OBJECT *contentType;
120 X509_ALGOR *contentEncryptionAlgorithm;
121 ASN1_OCTET_STRING *encryptedContent;
122 /* Content encryption algorithm and key */
123 const EVP_CIPHER *cipher;
124 unsigned char *key;
125 size_t keylen;
126 /* Set to 1 if we are debugging decrypt and don't fake keys for MMA */
127 int debug;
128};
129
130struct CMS_RecipientInfo_st {
131 int type;
132 union {
133 CMS_KeyTransRecipientInfo *ktri;
134 CMS_KeyAgreeRecipientInfo *kari;
135 CMS_KEKRecipientInfo *kekri;
136 CMS_PasswordRecipientInfo *pwri;
137 CMS_OtherRecipientInfo *ori;
138 } d;
139};
140
141typedef CMS_SignerIdentifier CMS_RecipientIdentifier;
142
143struct CMS_KeyTransRecipientInfo_st {
144 int32_t version;
145 CMS_RecipientIdentifier *rid;
146 X509_ALGOR *keyEncryptionAlgorithm;
147 ASN1_OCTET_STRING *encryptedKey;
148 /* Recipient Key and cert */
149 X509 *recip;
150 EVP_PKEY *pkey;
151 /* Public key context for this operation */
152 EVP_PKEY_CTX *pctx;
153};
154
155struct CMS_KeyAgreeRecipientInfo_st {
156 int32_t version;
157 CMS_OriginatorIdentifierOrKey *originator;
158 ASN1_OCTET_STRING *ukm;
159 X509_ALGOR *keyEncryptionAlgorithm;
160 STACK_OF(CMS_RecipientEncryptedKey) *recipientEncryptedKeys;
161 /* Public key context associated with current operation */
162 EVP_PKEY_CTX *pctx;
163 /* Cipher context for CEK wrapping */
164 EVP_CIPHER_CTX *ctx;
165};
166
167struct CMS_OriginatorIdentifierOrKey_st {
168 int type;
169 union {
170 CMS_IssuerAndSerialNumber *issuerAndSerialNumber;
171 ASN1_OCTET_STRING *subjectKeyIdentifier;
172 CMS_OriginatorPublicKey *originatorKey;
173 } d;
174};
175
176struct CMS_OriginatorPublicKey_st {
177 X509_ALGOR *algorithm;
178 ASN1_BIT_STRING *publicKey;
179};
180
181struct CMS_RecipientEncryptedKey_st {
182 CMS_KeyAgreeRecipientIdentifier *rid;
183 ASN1_OCTET_STRING *encryptedKey;
184 /* Public key associated with this recipient */
185 EVP_PKEY *pkey;
186};
187
188struct CMS_KeyAgreeRecipientIdentifier_st {
189 int type;
190 union {
191 CMS_IssuerAndSerialNumber *issuerAndSerialNumber;
192 CMS_RecipientKeyIdentifier *rKeyId;
193 } d;
194};
195
196struct CMS_RecipientKeyIdentifier_st {
197 ASN1_OCTET_STRING *subjectKeyIdentifier;
198 ASN1_GENERALIZEDTIME *date;
199 CMS_OtherKeyAttribute *other;
200};
201
202struct CMS_KEKRecipientInfo_st {
203 int32_t version;
204 CMS_KEKIdentifier *kekid;
205 X509_ALGOR *keyEncryptionAlgorithm;
206 ASN1_OCTET_STRING *encryptedKey;
207 /* Extra info: symmetric key to use */
208 unsigned char *key;
209 size_t keylen;
210};
211
212struct CMS_KEKIdentifier_st {
213 ASN1_OCTET_STRING *keyIdentifier;
214 ASN1_GENERALIZEDTIME *date;
215 CMS_OtherKeyAttribute *other;
216};
217
218struct CMS_PasswordRecipientInfo_st {
219 int32_t version;
220 X509_ALGOR *keyDerivationAlgorithm;
221 X509_ALGOR *keyEncryptionAlgorithm;
222 ASN1_OCTET_STRING *encryptedKey;
223 /* Extra info: password to use */
224 unsigned char *pass;
225 size_t passlen;
226};
227
228struct CMS_OtherRecipientInfo_st {
229 ASN1_OBJECT *oriType;
230 ASN1_TYPE *oriValue;
231};
232
233struct CMS_DigestedData_st {
234 int32_t version;
235 X509_ALGOR *digestAlgorithm;
236 CMS_EncapsulatedContentInfo *encapContentInfo;
237 ASN1_OCTET_STRING *digest;
238};
239
240struct CMS_EncryptedData_st {
241 int32_t version;
242 CMS_EncryptedContentInfo *encryptedContentInfo;
243 STACK_OF(X509_ATTRIBUTE) *unprotectedAttrs;
244};
245
246struct CMS_AuthenticatedData_st {
247 int32_t version;
248 CMS_OriginatorInfo *originatorInfo;
249 STACK_OF(CMS_RecipientInfo) *recipientInfos;
250 X509_ALGOR *macAlgorithm;
251 X509_ALGOR *digestAlgorithm;
252 CMS_EncapsulatedContentInfo *encapContentInfo;
253 STACK_OF(X509_ATTRIBUTE) *authAttrs;
254 ASN1_OCTET_STRING *mac;
255 STACK_OF(X509_ATTRIBUTE) *unauthAttrs;
256};
257
258struct CMS_CompressedData_st {
259 int32_t version;
260 X509_ALGOR *compressionAlgorithm;
261 STACK_OF(CMS_RecipientInfo) *recipientInfos;
262 CMS_EncapsulatedContentInfo *encapContentInfo;
263};
264
265struct CMS_RevocationInfoChoice_st {
266 int type;
267 union {
268 X509_CRL *crl;
269 CMS_OtherRevocationInfoFormat *other;
270 } d;
271};
272
273# define CMS_REVCHOICE_CRL 0
274# define CMS_REVCHOICE_OTHER 1
275
276struct CMS_OtherRevocationInfoFormat_st {
277 ASN1_OBJECT *otherRevInfoFormat;
278 ASN1_TYPE *otherRevInfo;
279};
280
281struct CMS_CertificateChoices {
282 int type;
283 union {
284 X509 *certificate;
285 ASN1_STRING *extendedCertificate; /* Obsolete */
286 ASN1_STRING *v1AttrCert; /* Left encoded for now */
287 ASN1_STRING *v2AttrCert; /* Left encoded for now */
288 CMS_OtherCertificateFormat *other;
289 } d;
290};
291
292# define CMS_CERTCHOICE_CERT 0
293# define CMS_CERTCHOICE_EXCERT 1
294# define CMS_CERTCHOICE_V1ACERT 2
295# define CMS_CERTCHOICE_V2ACERT 3
296# define CMS_CERTCHOICE_OTHER 4
297
298struct CMS_OtherCertificateFormat_st {
299 ASN1_OBJECT *otherCertFormat;
300 ASN1_TYPE *otherCert;
301};
302
303/*
304 * This is also defined in pkcs7.h but we duplicate it to allow the CMS code
305 * to be independent of PKCS#7
306 */
307
308struct CMS_IssuerAndSerialNumber_st {
309 X509_NAME *issuer;
310 ASN1_INTEGER *serialNumber;
311};
312
313struct CMS_OtherKeyAttribute_st {
314 ASN1_OBJECT *keyAttrId;
315 ASN1_TYPE *keyAttr;
316};
317
318/* ESS structures */
319
320# ifdef HEADER_X509V3_H
321
322struct CMS_ReceiptRequest_st {
323 ASN1_OCTET_STRING *signedContentIdentifier;
324 CMS_ReceiptsFrom *receiptsFrom;
325 STACK_OF(GENERAL_NAMES) *receiptsTo;
326};
327
328struct CMS_ReceiptsFrom_st {
329 int type;
330 union {
331 int32_t allOrFirstTier;
332 STACK_OF(GENERAL_NAMES) *receiptList;
333 } d;
334};
335# endif
336
337struct CMS_Receipt_st {
338 int32_t version;
339 ASN1_OBJECT *contentType;
340 ASN1_OCTET_STRING *signedContentIdentifier;
341 ASN1_OCTET_STRING *originatorSignatureValue;
342};
343
344DECLARE_ASN1_FUNCTIONS(CMS_ContentInfo)
345DECLARE_ASN1_ITEM(CMS_SignerInfo)
346DECLARE_ASN1_ITEM(CMS_IssuerAndSerialNumber)
347DECLARE_ASN1_ITEM(CMS_Attributes_Sign)
348DECLARE_ASN1_ITEM(CMS_Attributes_Verify)
349DECLARE_ASN1_ITEM(CMS_RecipientInfo)
350DECLARE_ASN1_ITEM(CMS_PasswordRecipientInfo)
351DECLARE_ASN1_ALLOC_FUNCTIONS(CMS_IssuerAndSerialNumber)
352
353# define CMS_SIGNERINFO_ISSUER_SERIAL 0
354# define CMS_SIGNERINFO_KEYIDENTIFIER 1
355
356# define CMS_RECIPINFO_ISSUER_SERIAL 0
357# define CMS_RECIPINFO_KEYIDENTIFIER 1
358
359# define CMS_REK_ISSUER_SERIAL 0
360# define CMS_REK_KEYIDENTIFIER 1
361
362# define CMS_OIK_ISSUER_SERIAL 0
363# define CMS_OIK_KEYIDENTIFIER 1
364# define CMS_OIK_PUBKEY 2
365
366BIO *cms_content_bio(CMS_ContentInfo *cms);
367
368CMS_ContentInfo *cms_Data_create(void);
369
370CMS_ContentInfo *cms_DigestedData_create(const EVP_MD *md);
371BIO *cms_DigestedData_init_bio(CMS_ContentInfo *cms);
372int cms_DigestedData_do_final(CMS_ContentInfo *cms, BIO *chain, int verify);
373
374BIO *cms_SignedData_init_bio(CMS_ContentInfo *cms);
375int cms_SignedData_final(CMS_ContentInfo *cms, BIO *chain);
376int cms_set1_SignerIdentifier(CMS_SignerIdentifier *sid, X509 *cert,
377 int type);
378int cms_SignerIdentifier_get0_signer_id(CMS_SignerIdentifier *sid,
379 ASN1_OCTET_STRING **keyid,
380 X509_NAME **issuer,
381 ASN1_INTEGER **sno);
382int cms_SignerIdentifier_cert_cmp(CMS_SignerIdentifier *sid, X509 *cert);
383
384CMS_ContentInfo *cms_CompressedData_create(int comp_nid);
385BIO *cms_CompressedData_init_bio(CMS_ContentInfo *cms);
386
387BIO *cms_DigestAlgorithm_init_bio(X509_ALGOR *digestAlgorithm);
388int cms_DigestAlgorithm_find_ctx(EVP_MD_CTX *mctx, BIO *chain,
389 X509_ALGOR *mdalg);
390
391int cms_ias_cert_cmp(CMS_IssuerAndSerialNumber *ias, X509 *cert);
392int cms_keyid_cert_cmp(ASN1_OCTET_STRING *keyid, X509 *cert);
393int cms_set1_ias(CMS_IssuerAndSerialNumber **pias, X509 *cert);
394int cms_set1_keyid(ASN1_OCTET_STRING **pkeyid, X509 *cert);
395
396BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec);
397BIO *cms_EncryptedData_init_bio(CMS_ContentInfo *cms);
398int cms_EncryptedContent_init(CMS_EncryptedContentInfo *ec,
399 const EVP_CIPHER *cipher,
400 const unsigned char *key, size_t keylen);
401
402int cms_Receipt_verify(CMS_ContentInfo *cms, CMS_ContentInfo *req_cms);
403int cms_msgSigDigest_add1(CMS_SignerInfo *dest, CMS_SignerInfo *src);
404ASN1_OCTET_STRING *cms_encode_Receipt(CMS_SignerInfo *si);
405
406BIO *cms_EnvelopedData_init_bio(CMS_ContentInfo *cms);
407CMS_EnvelopedData *cms_get0_enveloped(CMS_ContentInfo *cms);
408int cms_env_asn1_ctrl(CMS_RecipientInfo *ri, int cmd);
409int cms_pkey_get_ri_type(EVP_PKEY *pk);
410/* KARI routines */
411int cms_RecipientInfo_kari_init(CMS_RecipientInfo *ri, X509 *recip,
412 EVP_PKEY *pk, unsigned int flags);
413int cms_RecipientInfo_kari_encrypt(CMS_ContentInfo *cms,
414 CMS_RecipientInfo *ri);
415
416/* PWRI routines */
417int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri,
418 int en_de);
419
420DECLARE_ASN1_ITEM(CMS_CertificateChoices)
421DECLARE_ASN1_ITEM(CMS_DigestedData)
422DECLARE_ASN1_ITEM(CMS_EncryptedData)
423DECLARE_ASN1_ITEM(CMS_EnvelopedData)
424DECLARE_ASN1_ITEM(CMS_KEKRecipientInfo)
425DECLARE_ASN1_ITEM(CMS_KeyAgreeRecipientInfo)
426DECLARE_ASN1_ITEM(CMS_KeyTransRecipientInfo)
427DECLARE_ASN1_ITEM(CMS_OriginatorPublicKey)
428DECLARE_ASN1_ITEM(CMS_OtherKeyAttribute)
429DECLARE_ASN1_ITEM(CMS_Receipt)
430DECLARE_ASN1_ITEM(CMS_ReceiptRequest)
431DECLARE_ASN1_ITEM(CMS_RecipientEncryptedKey)
432DECLARE_ASN1_ITEM(CMS_RecipientKeyIdentifier)
433DECLARE_ASN1_ITEM(CMS_RevocationInfoChoice)
434DECLARE_ASN1_ITEM(CMS_SignedData)
435DECLARE_ASN1_ITEM(CMS_CompressedData)
436
437#endif
diff --git a/src/lib/libcrypto/cms/cms_lib.c b/src/lib/libcrypto/cms/cms_lib.c
new file mode 100644
index 0000000000..c2cac26010
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_lib.c
@@ -0,0 +1,587 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include <openssl/asn1t.h>
11#include <openssl/x509v3.h>
12#include <openssl/err.h>
13#include <openssl/pem.h>
14#include <openssl/bio.h>
15#include <openssl/asn1.h>
16#include <openssl/cms.h>
17#include "cms_lcl.h"
18
19IMPLEMENT_ASN1_FUNCTIONS(CMS_ContentInfo)
20IMPLEMENT_ASN1_PRINT_FUNCTION(CMS_ContentInfo)
21
22const ASN1_OBJECT *CMS_get0_type(const CMS_ContentInfo *cms)
23{
24 return cms->contentType;
25}
26
27CMS_ContentInfo *cms_Data_create(void)
28{
29 CMS_ContentInfo *cms;
30 cms = CMS_ContentInfo_new();
31 if (cms != NULL) {
32 cms->contentType = OBJ_nid2obj(NID_pkcs7_data);
33 /* Never detached */
34 CMS_set_detached(cms, 0);
35 }
36 return cms;
37}
38
39BIO *cms_content_bio(CMS_ContentInfo *cms)
40{
41 ASN1_OCTET_STRING **pos = CMS_get0_content(cms);
42 if (!pos)
43 return NULL;
44 /* If content detached data goes nowhere: create NULL BIO */
45 if (!*pos)
46 return BIO_new(BIO_s_null());
47 /*
48 * If content not detached and created return memory BIO
49 */
50 if (!*pos || ((*pos)->flags == ASN1_STRING_FLAG_CONT))
51 return BIO_new(BIO_s_mem());
52 /* Else content was read in: return read only BIO for it */
53 return BIO_new_mem_buf((*pos)->data, (*pos)->length);
54}
55
56BIO *CMS_dataInit(CMS_ContentInfo *cms, BIO *icont)
57{
58 BIO *cmsbio, *cont;
59 if (icont)
60 cont = icont;
61 else
62 cont = cms_content_bio(cms);
63 if (!cont) {
64 CMSerr(CMS_F_CMS_DATAINIT, CMS_R_NO_CONTENT);
65 return NULL;
66 }
67 switch (OBJ_obj2nid(cms->contentType)) {
68
69 case NID_pkcs7_data:
70 return cont;
71
72 case NID_pkcs7_signed:
73 cmsbio = cms_SignedData_init_bio(cms);
74 break;
75
76 case NID_pkcs7_digest:
77 cmsbio = cms_DigestedData_init_bio(cms);
78 break;
79#ifdef ZLIB
80 case NID_id_smime_ct_compressedData:
81 cmsbio = cms_CompressedData_init_bio(cms);
82 break;
83#endif
84
85 case NID_pkcs7_encrypted:
86 cmsbio = cms_EncryptedData_init_bio(cms);
87 break;
88
89 case NID_pkcs7_enveloped:
90 cmsbio = cms_EnvelopedData_init_bio(cms);
91 break;
92
93 default:
94 CMSerr(CMS_F_CMS_DATAINIT, CMS_R_UNSUPPORTED_TYPE);
95 return NULL;
96 }
97
98 if (cmsbio)
99 return BIO_push(cmsbio, cont);
100
101 if (!icont)
102 BIO_free(cont);
103 return NULL;
104
105}
106
107int CMS_dataFinal(CMS_ContentInfo *cms, BIO *cmsbio)
108{
109 ASN1_OCTET_STRING **pos = CMS_get0_content(cms);
110 if (!pos)
111 return 0;
112 /* If embedded content find memory BIO and set content */
113 if (*pos && ((*pos)->flags & ASN1_STRING_FLAG_CONT)) {
114 BIO *mbio;
115 unsigned char *cont;
116 long contlen;
117 mbio = BIO_find_type(cmsbio, BIO_TYPE_MEM);
118 if (!mbio) {
119 CMSerr(CMS_F_CMS_DATAFINAL, CMS_R_CONTENT_NOT_FOUND);
120 return 0;
121 }
122 contlen = BIO_get_mem_data(mbio, &cont);
123 /* Set bio as read only so its content can't be clobbered */
124 BIO_set_flags(mbio, BIO_FLAGS_MEM_RDONLY);
125 BIO_set_mem_eof_return(mbio, 0);
126 ASN1_STRING_set0(*pos, cont, contlen);
127 (*pos)->flags &= ~ASN1_STRING_FLAG_CONT;
128 }
129
130 switch (OBJ_obj2nid(cms->contentType)) {
131
132 case NID_pkcs7_data:
133 case NID_pkcs7_enveloped:
134 case NID_pkcs7_encrypted:
135 case NID_id_smime_ct_compressedData:
136 /* Nothing to do */
137 return 1;
138
139 case NID_pkcs7_signed:
140 return cms_SignedData_final(cms, cmsbio);
141
142 case NID_pkcs7_digest:
143 return cms_DigestedData_do_final(cms, cmsbio, 0);
144
145 default:
146 CMSerr(CMS_F_CMS_DATAFINAL, CMS_R_UNSUPPORTED_TYPE);
147 return 0;
148 }
149}
150
151/*
152 * Return an OCTET STRING pointer to content. This allows it to be accessed
153 * or set later.
154 */
155
156ASN1_OCTET_STRING **CMS_get0_content(CMS_ContentInfo *cms)
157{
158 switch (OBJ_obj2nid(cms->contentType)) {
159
160 case NID_pkcs7_data:
161 return &cms->d.data;
162
163 case NID_pkcs7_signed:
164 return &cms->d.signedData->encapContentInfo->eContent;
165
166 case NID_pkcs7_enveloped:
167 return &cms->d.envelopedData->encryptedContentInfo->encryptedContent;
168
169 case NID_pkcs7_digest:
170 return &cms->d.digestedData->encapContentInfo->eContent;
171
172 case NID_pkcs7_encrypted:
173 return &cms->d.encryptedData->encryptedContentInfo->encryptedContent;
174
175 case NID_id_smime_ct_authData:
176 return &cms->d.authenticatedData->encapContentInfo->eContent;
177
178 case NID_id_smime_ct_compressedData:
179 return &cms->d.compressedData->encapContentInfo->eContent;
180
181 default:
182 if (cms->d.other->type == V_ASN1_OCTET_STRING)
183 return &cms->d.other->value.octet_string;
184 CMSerr(CMS_F_CMS_GET0_CONTENT, CMS_R_UNSUPPORTED_CONTENT_TYPE);
185 return NULL;
186
187 }
188}
189
190/*
191 * Return an ASN1_OBJECT pointer to content type. This allows it to be
192 * accessed or set later.
193 */
194
195static ASN1_OBJECT **cms_get0_econtent_type(CMS_ContentInfo *cms)
196{
197 switch (OBJ_obj2nid(cms->contentType)) {
198
199 case NID_pkcs7_signed:
200 return &cms->d.signedData->encapContentInfo->eContentType;
201
202 case NID_pkcs7_enveloped:
203 return &cms->d.envelopedData->encryptedContentInfo->contentType;
204
205 case NID_pkcs7_digest:
206 return &cms->d.digestedData->encapContentInfo->eContentType;
207
208 case NID_pkcs7_encrypted:
209 return &cms->d.encryptedData->encryptedContentInfo->contentType;
210
211 case NID_id_smime_ct_authData:
212 return &cms->d.authenticatedData->encapContentInfo->eContentType;
213
214 case NID_id_smime_ct_compressedData:
215 return &cms->d.compressedData->encapContentInfo->eContentType;
216
217 default:
218 CMSerr(CMS_F_CMS_GET0_ECONTENT_TYPE, CMS_R_UNSUPPORTED_CONTENT_TYPE);
219 return NULL;
220
221 }
222}
223
224const ASN1_OBJECT *CMS_get0_eContentType(CMS_ContentInfo *cms)
225{
226 ASN1_OBJECT **petype;
227 petype = cms_get0_econtent_type(cms);
228 if (petype)
229 return *petype;
230 return NULL;
231}
232
233int CMS_set1_eContentType(CMS_ContentInfo *cms, const ASN1_OBJECT *oid)
234{
235 ASN1_OBJECT **petype, *etype;
236 petype = cms_get0_econtent_type(cms);
237 if (!petype)
238 return 0;
239 if (!oid)
240 return 1;
241 etype = OBJ_dup(oid);
242 if (!etype)
243 return 0;
244 ASN1_OBJECT_free(*petype);
245 *petype = etype;
246 return 1;
247}
248
249int CMS_is_detached(CMS_ContentInfo *cms)
250{
251 ASN1_OCTET_STRING **pos;
252 pos = CMS_get0_content(cms);
253 if (!pos)
254 return -1;
255 if (*pos)
256 return 0;
257 return 1;
258}
259
260int CMS_set_detached(CMS_ContentInfo *cms, int detached)
261{
262 ASN1_OCTET_STRING **pos;
263 pos = CMS_get0_content(cms);
264 if (!pos)
265 return 0;
266 if (detached) {
267 ASN1_OCTET_STRING_free(*pos);
268 *pos = NULL;
269 return 1;
270 }
271 if (*pos == NULL)
272 *pos = ASN1_OCTET_STRING_new();
273 if (*pos != NULL) {
274 /*
275 * NB: special flag to show content is created and not read in.
276 */
277 (*pos)->flags |= ASN1_STRING_FLAG_CONT;
278 return 1;
279 }
280 CMSerr(CMS_F_CMS_SET_DETACHED, ERR_R_MALLOC_FAILURE);
281 return 0;
282}
283
284/* Create a digest BIO from an X509_ALGOR structure */
285
286BIO *cms_DigestAlgorithm_init_bio(X509_ALGOR *digestAlgorithm)
287{
288 BIO *mdbio = NULL;
289 const ASN1_OBJECT *digestoid;
290 const EVP_MD *digest;
291 X509_ALGOR_get0(&digestoid, NULL, NULL, digestAlgorithm);
292 digest = EVP_get_digestbyobj(digestoid);
293 if (!digest) {
294 CMSerr(CMS_F_CMS_DIGESTALGORITHM_INIT_BIO,
295 CMS_R_UNKNOWN_DIGEST_ALGORITHM);
296 goto err;
297 }
298 mdbio = BIO_new(BIO_f_md());
299 if (mdbio == NULL || !BIO_set_md(mdbio, digest)) {
300 CMSerr(CMS_F_CMS_DIGESTALGORITHM_INIT_BIO, CMS_R_MD_BIO_INIT_ERROR);
301 goto err;
302 }
303 return mdbio;
304 err:
305 BIO_free(mdbio);
306 return NULL;
307}
308
309/* Locate a message digest content from a BIO chain based on SignerInfo */
310
311int cms_DigestAlgorithm_find_ctx(EVP_MD_CTX *mctx, BIO *chain,
312 X509_ALGOR *mdalg)
313{
314 int nid;
315 const ASN1_OBJECT *mdoid;
316 X509_ALGOR_get0(&mdoid, NULL, NULL, mdalg);
317 nid = OBJ_obj2nid(mdoid);
318 /* Look for digest type to match signature */
319 for (;;) {
320 EVP_MD_CTX *mtmp;
321 chain = BIO_find_type(chain, BIO_TYPE_MD);
322 if (chain == NULL) {
323 CMSerr(CMS_F_CMS_DIGESTALGORITHM_FIND_CTX,
324 CMS_R_NO_MATCHING_DIGEST);
325 return 0;
326 }
327 BIO_get_md_ctx(chain, &mtmp);
328 if (EVP_MD_CTX_type(mtmp) == nid
329 /*
330 * Workaround for broken implementations that use signature
331 * algorithm OID instead of digest.
332 */
333 || EVP_MD_pkey_type(EVP_MD_CTX_md(mtmp)) == nid)
334 return EVP_MD_CTX_copy_ex(mctx, mtmp);
335 chain = BIO_next(chain);
336 }
337}
338
339static STACK_OF(CMS_CertificateChoices)
340**cms_get0_certificate_choices(CMS_ContentInfo *cms)
341{
342 switch (OBJ_obj2nid(cms->contentType)) {
343
344 case NID_pkcs7_signed:
345 return &cms->d.signedData->certificates;
346
347 case NID_pkcs7_enveloped:
348 if (cms->d.envelopedData->originatorInfo == NULL)
349 return NULL;
350 return &cms->d.envelopedData->originatorInfo->certificates;
351
352 default:
353 CMSerr(CMS_F_CMS_GET0_CERTIFICATE_CHOICES,
354 CMS_R_UNSUPPORTED_CONTENT_TYPE);
355 return NULL;
356
357 }
358}
359
360CMS_CertificateChoices *CMS_add0_CertificateChoices(CMS_ContentInfo *cms)
361{
362 STACK_OF(CMS_CertificateChoices) **pcerts;
363 CMS_CertificateChoices *cch;
364 pcerts = cms_get0_certificate_choices(cms);
365 if (!pcerts)
366 return NULL;
367 if (!*pcerts)
368 *pcerts = sk_CMS_CertificateChoices_new_null();
369 if (!*pcerts)
370 return NULL;
371 cch = M_ASN1_new_of(CMS_CertificateChoices);
372 if (!cch)
373 return NULL;
374 if (!sk_CMS_CertificateChoices_push(*pcerts, cch)) {
375 M_ASN1_free_of(cch, CMS_CertificateChoices);
376 return NULL;
377 }
378 return cch;
379}
380
381int CMS_add0_cert(CMS_ContentInfo *cms, X509 *cert)
382{
383 CMS_CertificateChoices *cch;
384 STACK_OF(CMS_CertificateChoices) **pcerts;
385 int i;
386 pcerts = cms_get0_certificate_choices(cms);
387 if (!pcerts)
388 return 0;
389 for (i = 0; i < sk_CMS_CertificateChoices_num(*pcerts); i++) {
390 cch = sk_CMS_CertificateChoices_value(*pcerts, i);
391 if (cch->type == CMS_CERTCHOICE_CERT) {
392 if (!X509_cmp(cch->d.certificate, cert)) {
393 CMSerr(CMS_F_CMS_ADD0_CERT,
394 CMS_R_CERTIFICATE_ALREADY_PRESENT);
395 return 0;
396 }
397 }
398 }
399 cch = CMS_add0_CertificateChoices(cms);
400 if (!cch)
401 return 0;
402 cch->type = CMS_CERTCHOICE_CERT;
403 cch->d.certificate = cert;
404 return 1;
405}
406
407int CMS_add1_cert(CMS_ContentInfo *cms, X509 *cert)
408{
409 int r;
410 r = CMS_add0_cert(cms, cert);
411 if (r > 0)
412 X509_up_ref(cert);
413 return r;
414}
415
416static STACK_OF(CMS_RevocationInfoChoice)
417**cms_get0_revocation_choices(CMS_ContentInfo *cms)
418{
419 switch (OBJ_obj2nid(cms->contentType)) {
420
421 case NID_pkcs7_signed:
422 return &cms->d.signedData->crls;
423
424 case NID_pkcs7_enveloped:
425 if (cms->d.envelopedData->originatorInfo == NULL)
426 return NULL;
427 return &cms->d.envelopedData->originatorInfo->crls;
428
429 default:
430 CMSerr(CMS_F_CMS_GET0_REVOCATION_CHOICES,
431 CMS_R_UNSUPPORTED_CONTENT_TYPE);
432 return NULL;
433
434 }
435}
436
437CMS_RevocationInfoChoice *CMS_add0_RevocationInfoChoice(CMS_ContentInfo *cms)
438{
439 STACK_OF(CMS_RevocationInfoChoice) **pcrls;
440 CMS_RevocationInfoChoice *rch;
441 pcrls = cms_get0_revocation_choices(cms);
442 if (!pcrls)
443 return NULL;
444 if (!*pcrls)
445 *pcrls = sk_CMS_RevocationInfoChoice_new_null();
446 if (!*pcrls)
447 return NULL;
448 rch = M_ASN1_new_of(CMS_RevocationInfoChoice);
449 if (!rch)
450 return NULL;
451 if (!sk_CMS_RevocationInfoChoice_push(*pcrls, rch)) {
452 M_ASN1_free_of(rch, CMS_RevocationInfoChoice);
453 return NULL;
454 }
455 return rch;
456}
457
458int CMS_add0_crl(CMS_ContentInfo *cms, X509_CRL *crl)
459{
460 CMS_RevocationInfoChoice *rch;
461 rch = CMS_add0_RevocationInfoChoice(cms);
462 if (!rch)
463 return 0;
464 rch->type = CMS_REVCHOICE_CRL;
465 rch->d.crl = crl;
466 return 1;
467}
468
469int CMS_add1_crl(CMS_ContentInfo *cms, X509_CRL *crl)
470{
471 int r;
472 r = CMS_add0_crl(cms, crl);
473 if (r > 0)
474 X509_CRL_up_ref(crl);
475 return r;
476}
477
478STACK_OF(X509) *CMS_get1_certs(CMS_ContentInfo *cms)
479{
480 STACK_OF(X509) *certs = NULL;
481 CMS_CertificateChoices *cch;
482 STACK_OF(CMS_CertificateChoices) **pcerts;
483 int i;
484 pcerts = cms_get0_certificate_choices(cms);
485 if (!pcerts)
486 return NULL;
487 for (i = 0; i < sk_CMS_CertificateChoices_num(*pcerts); i++) {
488 cch = sk_CMS_CertificateChoices_value(*pcerts, i);
489 if (cch->type == 0) {
490 if (!certs) {
491 certs = sk_X509_new_null();
492 if (!certs)
493 return NULL;
494 }
495 if (!sk_X509_push(certs, cch->d.certificate)) {
496 sk_X509_pop_free(certs, X509_free);
497 return NULL;
498 }
499 X509_up_ref(cch->d.certificate);
500 }
501 }
502 return certs;
503
504}
505
506STACK_OF(X509_CRL) *CMS_get1_crls(CMS_ContentInfo *cms)
507{
508 STACK_OF(X509_CRL) *crls = NULL;
509 STACK_OF(CMS_RevocationInfoChoice) **pcrls;
510 CMS_RevocationInfoChoice *rch;
511 int i;
512 pcrls = cms_get0_revocation_choices(cms);
513 if (!pcrls)
514 return NULL;
515 for (i = 0; i < sk_CMS_RevocationInfoChoice_num(*pcrls); i++) {
516 rch = sk_CMS_RevocationInfoChoice_value(*pcrls, i);
517 if (rch->type == 0) {
518 if (!crls) {
519 crls = sk_X509_CRL_new_null();
520 if (!crls)
521 return NULL;
522 }
523 if (!sk_X509_CRL_push(crls, rch->d.crl)) {
524 sk_X509_CRL_pop_free(crls, X509_CRL_free);
525 return NULL;
526 }
527 X509_CRL_up_ref(rch->d.crl);
528 }
529 }
530 return crls;
531}
532
533int cms_ias_cert_cmp(CMS_IssuerAndSerialNumber *ias, X509 *cert)
534{
535 int ret;
536 ret = X509_NAME_cmp(ias->issuer, X509_get_issuer_name(cert));
537 if (ret)
538 return ret;
539 return ASN1_INTEGER_cmp(ias->serialNumber, X509_get_serialNumber(cert));
540}
541
542int cms_keyid_cert_cmp(ASN1_OCTET_STRING *keyid, X509 *cert)
543{
544 const ASN1_OCTET_STRING *cert_keyid = X509_get0_subject_key_id(cert);
545
546 if (cert_keyid == NULL)
547 return -1;
548 return ASN1_OCTET_STRING_cmp(keyid, cert_keyid);
549}
550
551int cms_set1_ias(CMS_IssuerAndSerialNumber **pias, X509 *cert)
552{
553 CMS_IssuerAndSerialNumber *ias;
554 ias = M_ASN1_new_of(CMS_IssuerAndSerialNumber);
555 if (!ias)
556 goto err;
557 if (!X509_NAME_set(&ias->issuer, X509_get_issuer_name(cert)))
558 goto err;
559 if (!ASN1_STRING_copy(ias->serialNumber, X509_get_serialNumber(cert)))
560 goto err;
561 M_ASN1_free_of(*pias, CMS_IssuerAndSerialNumber);
562 *pias = ias;
563 return 1;
564 err:
565 M_ASN1_free_of(ias, CMS_IssuerAndSerialNumber);
566 CMSerr(CMS_F_CMS_SET1_IAS, ERR_R_MALLOC_FAILURE);
567 return 0;
568}
569
570int cms_set1_keyid(ASN1_OCTET_STRING **pkeyid, X509 *cert)
571{
572 ASN1_OCTET_STRING *keyid = NULL;
573 const ASN1_OCTET_STRING *cert_keyid;
574 cert_keyid = X509_get0_subject_key_id(cert);
575 if (cert_keyid == NULL) {
576 CMSerr(CMS_F_CMS_SET1_KEYID, CMS_R_CERTIFICATE_HAS_NO_KEYID);
577 return 0;
578 }
579 keyid = ASN1_STRING_dup(cert_keyid);
580 if (!keyid) {
581 CMSerr(CMS_F_CMS_SET1_KEYID, ERR_R_MALLOC_FAILURE);
582 return 0;
583 }
584 ASN1_OCTET_STRING_free(*pkeyid);
585 *pkeyid = keyid;
586 return 1;
587}
diff --git a/src/lib/libcrypto/cms/cms_pwri.c b/src/lib/libcrypto/cms/cms_pwri.c
new file mode 100644
index 0000000000..26e3bdcf9e
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_pwri.c
@@ -0,0 +1,394 @@
1/*
2 * Copyright 2009-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include <openssl/rand.h>
17#include <openssl/aes.h>
18#include "cms_lcl.h"
19#include "internal/asn1_int.h"
20
21int CMS_RecipientInfo_set0_password(CMS_RecipientInfo *ri,
22 unsigned char *pass, ossl_ssize_t passlen)
23{
24 CMS_PasswordRecipientInfo *pwri;
25 if (ri->type != CMS_RECIPINFO_PASS) {
26 CMSerr(CMS_F_CMS_RECIPIENTINFO_SET0_PASSWORD, CMS_R_NOT_PWRI);
27 return 0;
28 }
29
30 pwri = ri->d.pwri;
31 pwri->pass = pass;
32 if (pass && passlen < 0)
33 passlen = strlen((char *)pass);
34 pwri->passlen = passlen;
35 return 1;
36}
37
38CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms,
39 int iter, int wrap_nid,
40 int pbe_nid,
41 unsigned char *pass,
42 ossl_ssize_t passlen,
43 const EVP_CIPHER *kekciph)
44{
45 CMS_RecipientInfo *ri = NULL;
46 CMS_EnvelopedData *env;
47 CMS_PasswordRecipientInfo *pwri;
48 EVP_CIPHER_CTX *ctx = NULL;
49 X509_ALGOR *encalg = NULL;
50 unsigned char iv[EVP_MAX_IV_LENGTH];
51 int ivlen;
52
53 env = cms_get0_enveloped(cms);
54 if (!env)
55 return NULL;
56
57 if (wrap_nid <= 0)
58 wrap_nid = NID_id_alg_PWRI_KEK;
59
60 if (pbe_nid <= 0)
61 pbe_nid = NID_id_pbkdf2;
62
63 /* Get from enveloped data */
64 if (kekciph == NULL)
65 kekciph = env->encryptedContentInfo->cipher;
66
67 if (kekciph == NULL) {
68 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, CMS_R_NO_CIPHER);
69 return NULL;
70 }
71 if (wrap_nid != NID_id_alg_PWRI_KEK) {
72 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD,
73 CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM);
74 return NULL;
75 }
76
77 /* Setup algorithm identifier for cipher */
78 encalg = X509_ALGOR_new();
79 if (encalg == NULL) {
80 goto merr;
81 }
82 ctx = EVP_CIPHER_CTX_new();
83
84 if (EVP_EncryptInit_ex(ctx, kekciph, NULL, NULL, NULL) <= 0) {
85 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_EVP_LIB);
86 goto err;
87 }
88
89 ivlen = EVP_CIPHER_CTX_iv_length(ctx);
90
91 if (ivlen > 0) {
92 if (RAND_bytes(iv, ivlen) <= 0)
93 goto err;
94 if (EVP_EncryptInit_ex(ctx, NULL, NULL, NULL, iv) <= 0) {
95 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_EVP_LIB);
96 goto err;
97 }
98 encalg->parameter = ASN1_TYPE_new();
99 if (!encalg->parameter) {
100 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_MALLOC_FAILURE);
101 goto err;
102 }
103 if (EVP_CIPHER_param_to_asn1(ctx, encalg->parameter) <= 0) {
104 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD,
105 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
106 goto err;
107 }
108 }
109
110 encalg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_type(ctx));
111
112 EVP_CIPHER_CTX_free(ctx);
113 ctx = NULL;
114
115 /* Initialize recipient info */
116 ri = M_ASN1_new_of(CMS_RecipientInfo);
117 if (ri == NULL)
118 goto merr;
119
120 ri->d.pwri = M_ASN1_new_of(CMS_PasswordRecipientInfo);
121 if (ri->d.pwri == NULL)
122 goto merr;
123 ri->type = CMS_RECIPINFO_PASS;
124
125 pwri = ri->d.pwri;
126 /* Since this is overwritten, free up empty structure already there */
127 X509_ALGOR_free(pwri->keyEncryptionAlgorithm);
128 pwri->keyEncryptionAlgorithm = X509_ALGOR_new();
129 if (pwri->keyEncryptionAlgorithm == NULL)
130 goto merr;
131 pwri->keyEncryptionAlgorithm->algorithm = OBJ_nid2obj(wrap_nid);
132 pwri->keyEncryptionAlgorithm->parameter = ASN1_TYPE_new();
133 if (pwri->keyEncryptionAlgorithm->parameter == NULL)
134 goto merr;
135
136 if (!ASN1_item_pack(encalg, ASN1_ITEM_rptr(X509_ALGOR),
137 &pwri->keyEncryptionAlgorithm->parameter->
138 value.sequence))
139 goto merr;
140 pwri->keyEncryptionAlgorithm->parameter->type = V_ASN1_SEQUENCE;
141
142 X509_ALGOR_free(encalg);
143 encalg = NULL;
144
145 /* Setup PBE algorithm */
146
147 pwri->keyDerivationAlgorithm = PKCS5_pbkdf2_set(iter, NULL, 0, -1, -1);
148
149 if (!pwri->keyDerivationAlgorithm)
150 goto err;
151
152 CMS_RecipientInfo_set0_password(ri, pass, passlen);
153 pwri->version = 0;
154
155 if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri))
156 goto merr;
157
158 return ri;
159
160 merr:
161 CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_MALLOC_FAILURE);
162 err:
163 EVP_CIPHER_CTX_free(ctx);
164 if (ri)
165 M_ASN1_free_of(ri, CMS_RecipientInfo);
166 X509_ALGOR_free(encalg);
167 return NULL;
168
169}
170
171/*
172 * This is an implementation of the key wrapping mechanism in RFC3211, at
173 * some point this should go into EVP.
174 */
175
176static int kek_unwrap_key(unsigned char *out, size_t *outlen,
177 const unsigned char *in, size_t inlen,
178 EVP_CIPHER_CTX *ctx)
179{
180 size_t blocklen = EVP_CIPHER_CTX_block_size(ctx);
181 unsigned char *tmp;
182 int outl, rv = 0;
183 if (inlen < 2 * blocklen) {
184 /* too small */
185 return 0;
186 }
187 if (inlen % blocklen) {
188 /* Invalid size */
189 return 0;
190 }
191 if ((tmp = OPENSSL_malloc(inlen)) == NULL) {
192 CMSerr(CMS_F_KEK_UNWRAP_KEY, ERR_R_MALLOC_FAILURE);
193 return 0;
194 }
195 /* setup IV by decrypting last two blocks */
196 if (!EVP_DecryptUpdate(ctx, tmp + inlen - 2 * blocklen, &outl,
197 in + inlen - 2 * blocklen, blocklen * 2)
198 /*
199 * Do a decrypt of last decrypted block to set IV to correct value
200 * output it to start of buffer so we don't corrupt decrypted block
201 * this works because buffer is at least two block lengths long.
202 */
203 || !EVP_DecryptUpdate(ctx, tmp, &outl,
204 tmp + inlen - blocklen, blocklen)
205 /* Can now decrypt first n - 1 blocks */
206 || !EVP_DecryptUpdate(ctx, tmp, &outl, in, inlen - blocklen)
207
208 /* Reset IV to original value */
209 || !EVP_DecryptInit_ex(ctx, NULL, NULL, NULL, NULL)
210 /* Decrypt again */
211 || !EVP_DecryptUpdate(ctx, tmp, &outl, tmp, inlen))
212 goto err;
213 /* Check check bytes */
214 if (((tmp[1] ^ tmp[4]) & (tmp[2] ^ tmp[5]) & (tmp[3] ^ tmp[6])) != 0xff) {
215 /* Check byte failure */
216 goto err;
217 }
218 if (inlen < (size_t)(tmp[0] - 4)) {
219 /* Invalid length value */
220 goto err;
221 }
222 *outlen = (size_t)tmp[0];
223 memcpy(out, tmp + 4, *outlen);
224 rv = 1;
225 err:
226 OPENSSL_clear_free(tmp, inlen);
227 return rv;
228
229}
230
231static int kek_wrap_key(unsigned char *out, size_t *outlen,
232 const unsigned char *in, size_t inlen,
233 EVP_CIPHER_CTX *ctx)
234{
235 size_t blocklen = EVP_CIPHER_CTX_block_size(ctx);
236 size_t olen;
237 int dummy;
238 /*
239 * First decide length of output buffer: need header and round up to
240 * multiple of block length.
241 */
242 olen = (inlen + 4 + blocklen - 1) / blocklen;
243 olen *= blocklen;
244 if (olen < 2 * blocklen) {
245 /* Key too small */
246 return 0;
247 }
248 if (inlen > 0xFF) {
249 /* Key too large */
250 return 0;
251 }
252 if (out) {
253 /* Set header */
254 out[0] = (unsigned char)inlen;
255 out[1] = in[0] ^ 0xFF;
256 out[2] = in[1] ^ 0xFF;
257 out[3] = in[2] ^ 0xFF;
258 memcpy(out + 4, in, inlen);
259 /* Add random padding to end */
260 if (olen > inlen + 4
261 && RAND_bytes(out + 4 + inlen, olen - 4 - inlen) <= 0)
262 return 0;
263 /* Encrypt twice */
264 if (!EVP_EncryptUpdate(ctx, out, &dummy, out, olen)
265 || !EVP_EncryptUpdate(ctx, out, &dummy, out, olen))
266 return 0;
267 }
268
269 *outlen = olen;
270
271 return 1;
272}
273
274/* Encrypt/Decrypt content key in PWRI recipient info */
275
276int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri,
277 int en_de)
278{
279 CMS_EncryptedContentInfo *ec;
280 CMS_PasswordRecipientInfo *pwri;
281 int r = 0;
282 X509_ALGOR *algtmp, *kekalg = NULL;
283 EVP_CIPHER_CTX *kekctx = NULL;
284 const EVP_CIPHER *kekcipher;
285 unsigned char *key = NULL;
286 size_t keylen;
287
288 ec = cms->d.envelopedData->encryptedContentInfo;
289
290 pwri = ri->d.pwri;
291
292 if (!pwri->pass) {
293 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_NO_PASSWORD);
294 return 0;
295 }
296 algtmp = pwri->keyEncryptionAlgorithm;
297
298 if (!algtmp || OBJ_obj2nid(algtmp->algorithm) != NID_id_alg_PWRI_KEK) {
299 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT,
300 CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM);
301 return 0;
302 }
303
304 kekalg = ASN1_TYPE_unpack_sequence(ASN1_ITEM_rptr(X509_ALGOR),
305 algtmp->parameter);
306
307 if (kekalg == NULL) {
308 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT,
309 CMS_R_INVALID_KEY_ENCRYPTION_PARAMETER);
310 return 0;
311 }
312
313 kekcipher = EVP_get_cipherbyobj(kekalg->algorithm);
314
315 if (!kekcipher) {
316 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_UNKNOWN_CIPHER);
317 return 0;
318 }
319
320 kekctx = EVP_CIPHER_CTX_new();
321 if (kekctx == NULL) {
322 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_MALLOC_FAILURE);
323 return 0;
324 }
325 /* Fixup cipher based on AlgorithmIdentifier to set IV etc */
326 if (!EVP_CipherInit_ex(kekctx, kekcipher, NULL, NULL, NULL, en_de))
327 goto err;
328 EVP_CIPHER_CTX_set_padding(kekctx, 0);
329 if (EVP_CIPHER_asn1_to_param(kekctx, kekalg->parameter) <= 0) {
330 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT,
331 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
332 goto err;
333 }
334
335 algtmp = pwri->keyDerivationAlgorithm;
336
337 /* Finish password based key derivation to setup key in "ctx" */
338
339 if (EVP_PBE_CipherInit(algtmp->algorithm,
340 (char *)pwri->pass, pwri->passlen,
341 algtmp->parameter, kekctx, en_de) < 0) {
342 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_EVP_LIB);
343 goto err;
344 }
345
346 /* Finally wrap/unwrap the key */
347
348 if (en_de) {
349
350 if (!kek_wrap_key(NULL, &keylen, ec->key, ec->keylen, kekctx))
351 goto err;
352
353 key = OPENSSL_malloc(keylen);
354
355 if (key == NULL)
356 goto err;
357
358 if (!kek_wrap_key(key, &keylen, ec->key, ec->keylen, kekctx))
359 goto err;
360 pwri->encryptedKey->data = key;
361 pwri->encryptedKey->length = keylen;
362 } else {
363 key = OPENSSL_malloc(pwri->encryptedKey->length);
364
365 if (key == NULL) {
366 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_MALLOC_FAILURE);
367 goto err;
368 }
369 if (!kek_unwrap_key(key, &keylen,
370 pwri->encryptedKey->data,
371 pwri->encryptedKey->length, kekctx)) {
372 CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_UNWRAP_FAILURE);
373 goto err;
374 }
375
376 OPENSSL_clear_free(ec->key, ec->keylen);
377 ec->key = key;
378 ec->keylen = keylen;
379
380 }
381
382 r = 1;
383
384 err:
385
386 EVP_CIPHER_CTX_free(kekctx);
387
388 if (!r)
389 OPENSSL_free(key);
390 X509_ALGOR_free(kekalg);
391
392 return r;
393
394}
diff --git a/src/lib/libcrypto/cms/cms_sd.c b/src/lib/libcrypto/cms/cms_sd.c
new file mode 100644
index 0000000000..ff2d540b6a
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_sd.c
@@ -0,0 +1,926 @@
1/*
2 * Copyright 2008-2016 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/pem.h>
13#include <openssl/x509.h>
14#include <openssl/x509v3.h>
15#include <openssl/err.h>
16#include <openssl/cms.h>
17#include "cms_lcl.h"
18#include "internal/asn1_int.h"
19#include "internal/evp_int.h"
20
21/* CMS SignedData Utilities */
22
23static CMS_SignedData *cms_get0_signed(CMS_ContentInfo *cms)
24{
25 if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_signed) {
26 CMSerr(CMS_F_CMS_GET0_SIGNED, CMS_R_CONTENT_TYPE_NOT_SIGNED_DATA);
27 return NULL;
28 }
29 return cms->d.signedData;
30}
31
32static CMS_SignedData *cms_signed_data_init(CMS_ContentInfo *cms)
33{
34 if (cms->d.other == NULL) {
35 cms->d.signedData = M_ASN1_new_of(CMS_SignedData);
36 if (!cms->d.signedData) {
37 CMSerr(CMS_F_CMS_SIGNED_DATA_INIT, ERR_R_MALLOC_FAILURE);
38 return NULL;
39 }
40 cms->d.signedData->version = 1;
41 cms->d.signedData->encapContentInfo->eContentType =
42 OBJ_nid2obj(NID_pkcs7_data);
43 cms->d.signedData->encapContentInfo->partial = 1;
44 ASN1_OBJECT_free(cms->contentType);
45 cms->contentType = OBJ_nid2obj(NID_pkcs7_signed);
46 return cms->d.signedData;
47 }
48 return cms_get0_signed(cms);
49}
50
51/* Just initialise SignedData e.g. for certs only structure */
52
53int CMS_SignedData_init(CMS_ContentInfo *cms)
54{
55 if (cms_signed_data_init(cms))
56 return 1;
57 else
58 return 0;
59}
60
61/* Check structures and fixup version numbers (if necessary) */
62
63static void cms_sd_set_version(CMS_SignedData *sd)
64{
65 int i;
66 CMS_CertificateChoices *cch;
67 CMS_RevocationInfoChoice *rch;
68 CMS_SignerInfo *si;
69
70 for (i = 0; i < sk_CMS_CertificateChoices_num(sd->certificates); i++) {
71 cch = sk_CMS_CertificateChoices_value(sd->certificates, i);
72 if (cch->type == CMS_CERTCHOICE_OTHER) {
73 if (sd->version < 5)
74 sd->version = 5;
75 } else if (cch->type == CMS_CERTCHOICE_V2ACERT) {
76 if (sd->version < 4)
77 sd->version = 4;
78 } else if (cch->type == CMS_CERTCHOICE_V1ACERT) {
79 if (sd->version < 3)
80 sd->version = 3;
81 }
82 }
83
84 for (i = 0; i < sk_CMS_RevocationInfoChoice_num(sd->crls); i++) {
85 rch = sk_CMS_RevocationInfoChoice_value(sd->crls, i);
86 if (rch->type == CMS_REVCHOICE_OTHER) {
87 if (sd->version < 5)
88 sd->version = 5;
89 }
90 }
91
92 if ((OBJ_obj2nid(sd->encapContentInfo->eContentType) != NID_pkcs7_data)
93 && (sd->version < 3))
94 sd->version = 3;
95
96 for (i = 0; i < sk_CMS_SignerInfo_num(sd->signerInfos); i++) {
97 si = sk_CMS_SignerInfo_value(sd->signerInfos, i);
98 if (si->sid->type == CMS_SIGNERINFO_KEYIDENTIFIER) {
99 if (si->version < 3)
100 si->version = 3;
101 if (sd->version < 3)
102 sd->version = 3;
103 } else if (si->version < 1)
104 si->version = 1;
105 }
106
107 if (sd->version < 1)
108 sd->version = 1;
109
110}
111
112/* Copy an existing messageDigest value */
113
114static int cms_copy_messageDigest(CMS_ContentInfo *cms, CMS_SignerInfo *si)
115{
116 STACK_OF(CMS_SignerInfo) *sinfos;
117 CMS_SignerInfo *sitmp;
118 int i;
119 sinfos = CMS_get0_SignerInfos(cms);
120 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
121 ASN1_OCTET_STRING *messageDigest;
122 sitmp = sk_CMS_SignerInfo_value(sinfos, i);
123 if (sitmp == si)
124 continue;
125 if (CMS_signed_get_attr_count(sitmp) < 0)
126 continue;
127 if (OBJ_cmp(si->digestAlgorithm->algorithm,
128 sitmp->digestAlgorithm->algorithm))
129 continue;
130 messageDigest = CMS_signed_get0_data_by_OBJ(sitmp,
131 OBJ_nid2obj
132 (NID_pkcs9_messageDigest),
133 -3, V_ASN1_OCTET_STRING);
134 if (!messageDigest) {
135 CMSerr(CMS_F_CMS_COPY_MESSAGEDIGEST,
136 CMS_R_ERROR_READING_MESSAGEDIGEST_ATTRIBUTE);
137 return 0;
138 }
139
140 if (CMS_signed_add1_attr_by_NID(si, NID_pkcs9_messageDigest,
141 V_ASN1_OCTET_STRING,
142 messageDigest, -1))
143 return 1;
144 else
145 return 0;
146 }
147 CMSerr(CMS_F_CMS_COPY_MESSAGEDIGEST, CMS_R_NO_MATCHING_DIGEST);
148 return 0;
149}
150
151int cms_set1_SignerIdentifier(CMS_SignerIdentifier *sid, X509 *cert, int type)
152{
153 switch (type) {
154 case CMS_SIGNERINFO_ISSUER_SERIAL:
155 if (!cms_set1_ias(&sid->d.issuerAndSerialNumber, cert))
156 return 0;
157 break;
158
159 case CMS_SIGNERINFO_KEYIDENTIFIER:
160 if (!cms_set1_keyid(&sid->d.subjectKeyIdentifier, cert))
161 return 0;
162 break;
163
164 default:
165 CMSerr(CMS_F_CMS_SET1_SIGNERIDENTIFIER, CMS_R_UNKNOWN_ID);
166 return 0;
167 }
168
169 sid->type = type;
170
171 return 1;
172}
173
174int cms_SignerIdentifier_get0_signer_id(CMS_SignerIdentifier *sid,
175 ASN1_OCTET_STRING **keyid,
176 X509_NAME **issuer,
177 ASN1_INTEGER **sno)
178{
179 if (sid->type == CMS_SIGNERINFO_ISSUER_SERIAL) {
180 if (issuer)
181 *issuer = sid->d.issuerAndSerialNumber->issuer;
182 if (sno)
183 *sno = sid->d.issuerAndSerialNumber->serialNumber;
184 } else if (sid->type == CMS_SIGNERINFO_KEYIDENTIFIER) {
185 if (keyid)
186 *keyid = sid->d.subjectKeyIdentifier;
187 } else
188 return 0;
189 return 1;
190}
191
192int cms_SignerIdentifier_cert_cmp(CMS_SignerIdentifier *sid, X509 *cert)
193{
194 if (sid->type == CMS_SIGNERINFO_ISSUER_SERIAL)
195 return cms_ias_cert_cmp(sid->d.issuerAndSerialNumber, cert);
196 else if (sid->type == CMS_SIGNERINFO_KEYIDENTIFIER)
197 return cms_keyid_cert_cmp(sid->d.subjectKeyIdentifier, cert);
198 else
199 return -1;
200}
201
202static int cms_sd_asn1_ctrl(CMS_SignerInfo *si, int cmd)
203{
204 EVP_PKEY *pkey = si->pkey;
205 int i;
206 if (!pkey->ameth || !pkey->ameth->pkey_ctrl)
207 return 1;
208 i = pkey->ameth->pkey_ctrl(pkey, ASN1_PKEY_CTRL_CMS_SIGN, cmd, si);
209 if (i == -2) {
210 CMSerr(CMS_F_CMS_SD_ASN1_CTRL, CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
211 return 0;
212 }
213 if (i <= 0) {
214 CMSerr(CMS_F_CMS_SD_ASN1_CTRL, CMS_R_CTRL_FAILURE);
215 return 0;
216 }
217 return 1;
218}
219
220CMS_SignerInfo *CMS_add1_signer(CMS_ContentInfo *cms,
221 X509 *signer, EVP_PKEY *pk, const EVP_MD *md,
222 unsigned int flags)
223{
224 CMS_SignedData *sd;
225 CMS_SignerInfo *si = NULL;
226 X509_ALGOR *alg;
227 int i, type;
228 if (!X509_check_private_key(signer, pk)) {
229 CMSerr(CMS_F_CMS_ADD1_SIGNER,
230 CMS_R_PRIVATE_KEY_DOES_NOT_MATCH_CERTIFICATE);
231 return NULL;
232 }
233 sd = cms_signed_data_init(cms);
234 if (!sd)
235 goto err;
236 si = M_ASN1_new_of(CMS_SignerInfo);
237 if (!si)
238 goto merr;
239 /* Call for side-effect of computing hash and caching extensions */
240 X509_check_purpose(signer, -1, -1);
241
242 X509_up_ref(signer);
243 EVP_PKEY_up_ref(pk);
244
245 si->pkey = pk;
246 si->signer = signer;
247 si->mctx = EVP_MD_CTX_new();
248 si->pctx = NULL;
249
250 if (si->mctx == NULL) {
251 CMSerr(CMS_F_CMS_ADD1_SIGNER, ERR_R_MALLOC_FAILURE);
252 goto err;
253 }
254
255 if (flags & CMS_USE_KEYID) {
256 si->version = 3;
257 if (sd->version < 3)
258 sd->version = 3;
259 type = CMS_SIGNERINFO_KEYIDENTIFIER;
260 } else {
261 type = CMS_SIGNERINFO_ISSUER_SERIAL;
262 si->version = 1;
263 }
264
265 if (!cms_set1_SignerIdentifier(si->sid, signer, type))
266 goto err;
267
268 if (md == NULL) {
269 int def_nid;
270 if (EVP_PKEY_get_default_digest_nid(pk, &def_nid) <= 0)
271 goto err;
272 md = EVP_get_digestbynid(def_nid);
273 if (md == NULL) {
274 CMSerr(CMS_F_CMS_ADD1_SIGNER, CMS_R_NO_DEFAULT_DIGEST);
275 goto err;
276 }
277 }
278
279 if (!md) {
280 CMSerr(CMS_F_CMS_ADD1_SIGNER, CMS_R_NO_DIGEST_SET);
281 goto err;
282 }
283
284 X509_ALGOR_set_md(si->digestAlgorithm, md);
285
286 /* See if digest is present in digestAlgorithms */
287 for (i = 0; i < sk_X509_ALGOR_num(sd->digestAlgorithms); i++) {
288 const ASN1_OBJECT *aoid;
289 alg = sk_X509_ALGOR_value(sd->digestAlgorithms, i);
290 X509_ALGOR_get0(&aoid, NULL, NULL, alg);
291 if (OBJ_obj2nid(aoid) == EVP_MD_type(md))
292 break;
293 }
294
295 if (i == sk_X509_ALGOR_num(sd->digestAlgorithms)) {
296 alg = X509_ALGOR_new();
297 if (alg == NULL)
298 goto merr;
299 X509_ALGOR_set_md(alg, md);
300 if (!sk_X509_ALGOR_push(sd->digestAlgorithms, alg)) {
301 X509_ALGOR_free(alg);
302 goto merr;
303 }
304 }
305
306 if (!(flags & CMS_KEY_PARAM) && !cms_sd_asn1_ctrl(si, 0))
307 goto err;
308 if (!(flags & CMS_NOATTR)) {
309 /*
310 * Initialize signed attributes structure so other attributes
311 * such as signing time etc are added later even if we add none here.
312 */
313 if (!si->signedAttrs) {
314 si->signedAttrs = sk_X509_ATTRIBUTE_new_null();
315 if (!si->signedAttrs)
316 goto merr;
317 }
318
319 if (!(flags & CMS_NOSMIMECAP)) {
320 STACK_OF(X509_ALGOR) *smcap = NULL;
321 i = CMS_add_standard_smimecap(&smcap);
322 if (i)
323 i = CMS_add_smimecap(si, smcap);
324 sk_X509_ALGOR_pop_free(smcap, X509_ALGOR_free);
325 if (!i)
326 goto merr;
327 }
328 if (flags & CMS_REUSE_DIGEST) {
329 if (!cms_copy_messageDigest(cms, si))
330 goto err;
331 if (!(flags & (CMS_PARTIAL | CMS_KEY_PARAM)) &&
332 !CMS_SignerInfo_sign(si))
333 goto err;
334 }
335 }
336
337 if (!(flags & CMS_NOCERTS)) {
338 /* NB ignore -1 return for duplicate cert */
339 if (!CMS_add1_cert(cms, signer))
340 goto merr;
341 }
342
343 if (flags & CMS_KEY_PARAM) {
344 if (flags & CMS_NOATTR) {
345 si->pctx = EVP_PKEY_CTX_new(si->pkey, NULL);
346 if (si->pctx == NULL)
347 goto err;
348 if (EVP_PKEY_sign_init(si->pctx) <= 0)
349 goto err;
350 if (EVP_PKEY_CTX_set_signature_md(si->pctx, md) <= 0)
351 goto err;
352 } else if (EVP_DigestSignInit(si->mctx, &si->pctx, md, NULL, pk) <=
353 0)
354 goto err;
355 }
356
357 if (!sd->signerInfos)
358 sd->signerInfos = sk_CMS_SignerInfo_new_null();
359 if (!sd->signerInfos || !sk_CMS_SignerInfo_push(sd->signerInfos, si))
360 goto merr;
361
362 return si;
363
364 merr:
365 CMSerr(CMS_F_CMS_ADD1_SIGNER, ERR_R_MALLOC_FAILURE);
366 err:
367 M_ASN1_free_of(si, CMS_SignerInfo);
368 return NULL;
369
370}
371
372static int cms_add1_signingTime(CMS_SignerInfo *si, ASN1_TIME *t)
373{
374 ASN1_TIME *tt;
375 int r = 0;
376 if (t)
377 tt = t;
378 else
379 tt = X509_gmtime_adj(NULL, 0);
380
381 if (!tt)
382 goto merr;
383
384 if (CMS_signed_add1_attr_by_NID(si, NID_pkcs9_signingTime,
385 tt->type, tt, -1) <= 0)
386 goto merr;
387
388 r = 1;
389
390 merr:
391
392 if (!t)
393 ASN1_TIME_free(tt);
394
395 if (!r)
396 CMSerr(CMS_F_CMS_ADD1_SIGNINGTIME, ERR_R_MALLOC_FAILURE);
397
398 return r;
399
400}
401
402EVP_PKEY_CTX *CMS_SignerInfo_get0_pkey_ctx(CMS_SignerInfo *si)
403{
404 return si->pctx;
405}
406
407EVP_MD_CTX *CMS_SignerInfo_get0_md_ctx(CMS_SignerInfo *si)
408{
409 return si->mctx;
410}
411
412STACK_OF(CMS_SignerInfo) *CMS_get0_SignerInfos(CMS_ContentInfo *cms)
413{
414 CMS_SignedData *sd;
415 sd = cms_get0_signed(cms);
416 if (!sd)
417 return NULL;
418 return sd->signerInfos;
419}
420
421STACK_OF(X509) *CMS_get0_signers(CMS_ContentInfo *cms)
422{
423 STACK_OF(X509) *signers = NULL;
424 STACK_OF(CMS_SignerInfo) *sinfos;
425 CMS_SignerInfo *si;
426 int i;
427 sinfos = CMS_get0_SignerInfos(cms);
428 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
429 si = sk_CMS_SignerInfo_value(sinfos, i);
430 if (si->signer) {
431 if (!signers) {
432 signers = sk_X509_new_null();
433 if (!signers)
434 return NULL;
435 }
436 if (!sk_X509_push(signers, si->signer)) {
437 sk_X509_free(signers);
438 return NULL;
439 }
440 }
441 }
442 return signers;
443}
444
445void CMS_SignerInfo_set1_signer_cert(CMS_SignerInfo *si, X509 *signer)
446{
447 if (signer) {
448 X509_up_ref(signer);
449 EVP_PKEY_free(si->pkey);
450 si->pkey = X509_get_pubkey(signer);
451 }
452 X509_free(si->signer);
453 si->signer = signer;
454}
455
456int CMS_SignerInfo_get0_signer_id(CMS_SignerInfo *si,
457 ASN1_OCTET_STRING **keyid,
458 X509_NAME **issuer, ASN1_INTEGER **sno)
459{
460 return cms_SignerIdentifier_get0_signer_id(si->sid, keyid, issuer, sno);
461}
462
463int CMS_SignerInfo_cert_cmp(CMS_SignerInfo *si, X509 *cert)
464{
465 return cms_SignerIdentifier_cert_cmp(si->sid, cert);
466}
467
468int CMS_set1_signers_certs(CMS_ContentInfo *cms, STACK_OF(X509) *scerts,
469 unsigned int flags)
470{
471 CMS_SignedData *sd;
472 CMS_SignerInfo *si;
473 CMS_CertificateChoices *cch;
474 STACK_OF(CMS_CertificateChoices) *certs;
475 X509 *x;
476 int i, j;
477 int ret = 0;
478 sd = cms_get0_signed(cms);
479 if (!sd)
480 return -1;
481 certs = sd->certificates;
482 for (i = 0; i < sk_CMS_SignerInfo_num(sd->signerInfos); i++) {
483 si = sk_CMS_SignerInfo_value(sd->signerInfos, i);
484 if (si->signer)
485 continue;
486
487 for (j = 0; j < sk_X509_num(scerts); j++) {
488 x = sk_X509_value(scerts, j);
489 if (CMS_SignerInfo_cert_cmp(si, x) == 0) {
490 CMS_SignerInfo_set1_signer_cert(si, x);
491 ret++;
492 break;
493 }
494 }
495
496 if (si->signer || (flags & CMS_NOINTERN))
497 continue;
498
499 for (j = 0; j < sk_CMS_CertificateChoices_num(certs); j++) {
500 cch = sk_CMS_CertificateChoices_value(certs, j);
501 if (cch->type != 0)
502 continue;
503 x = cch->d.certificate;
504 if (CMS_SignerInfo_cert_cmp(si, x) == 0) {
505 CMS_SignerInfo_set1_signer_cert(si, x);
506 ret++;
507 break;
508 }
509 }
510 }
511 return ret;
512}
513
514void CMS_SignerInfo_get0_algs(CMS_SignerInfo *si, EVP_PKEY **pk,
515 X509 **signer, X509_ALGOR **pdig,
516 X509_ALGOR **psig)
517{
518 if (pk)
519 *pk = si->pkey;
520 if (signer)
521 *signer = si->signer;
522 if (pdig)
523 *pdig = si->digestAlgorithm;
524 if (psig)
525 *psig = si->signatureAlgorithm;
526}
527
528ASN1_OCTET_STRING *CMS_SignerInfo_get0_signature(CMS_SignerInfo *si)
529{
530 return si->signature;
531}
532
533static int cms_SignerInfo_content_sign(CMS_ContentInfo *cms,
534 CMS_SignerInfo *si, BIO *chain)
535{
536 EVP_MD_CTX *mctx = EVP_MD_CTX_new();
537 int r = 0;
538 EVP_PKEY_CTX *pctx = NULL;
539
540 if (mctx == NULL) {
541 CMSerr(CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, ERR_R_MALLOC_FAILURE);
542 return 0;
543 }
544
545 if (!si->pkey) {
546 CMSerr(CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, CMS_R_NO_PRIVATE_KEY);
547 goto err;
548 }
549
550 if (!cms_DigestAlgorithm_find_ctx(mctx, chain, si->digestAlgorithm))
551 goto err;
552 /* Set SignerInfo algorithm details if we used custom parameter */
553 if (si->pctx && !cms_sd_asn1_ctrl(si, 0))
554 goto err;
555
556 /*
557 * If any signed attributes calculate and add messageDigest attribute
558 */
559
560 if (CMS_signed_get_attr_count(si) >= 0) {
561 ASN1_OBJECT *ctype =
562 cms->d.signedData->encapContentInfo->eContentType;
563 unsigned char md[EVP_MAX_MD_SIZE];
564 unsigned int mdlen;
565 if (!EVP_DigestFinal_ex(mctx, md, &mdlen))
566 goto err;
567 if (!CMS_signed_add1_attr_by_NID(si, NID_pkcs9_messageDigest,
568 V_ASN1_OCTET_STRING, md, mdlen))
569 goto err;
570 /* Copy content type across */
571 if (CMS_signed_add1_attr_by_NID(si, NID_pkcs9_contentType,
572 V_ASN1_OBJECT, ctype, -1) <= 0)
573 goto err;
574 if (!CMS_SignerInfo_sign(si))
575 goto err;
576 } else if (si->pctx) {
577 unsigned char *sig;
578 size_t siglen;
579 unsigned char md[EVP_MAX_MD_SIZE];
580 unsigned int mdlen;
581 pctx = si->pctx;
582 if (!EVP_DigestFinal_ex(mctx, md, &mdlen))
583 goto err;
584 siglen = EVP_PKEY_size(si->pkey);
585 sig = OPENSSL_malloc(siglen);
586 if (sig == NULL) {
587 CMSerr(CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, ERR_R_MALLOC_FAILURE);
588 goto err;
589 }
590 if (EVP_PKEY_sign(pctx, sig, &siglen, md, mdlen) <= 0) {
591 OPENSSL_free(sig);
592 goto err;
593 }
594 ASN1_STRING_set0(si->signature, sig, siglen);
595 } else {
596 unsigned char *sig;
597 unsigned int siglen;
598 sig = OPENSSL_malloc(EVP_PKEY_size(si->pkey));
599 if (sig == NULL) {
600 CMSerr(CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, ERR_R_MALLOC_FAILURE);
601 goto err;
602 }
603 if (!EVP_SignFinal(mctx, sig, &siglen, si->pkey)) {
604 CMSerr(CMS_F_CMS_SIGNERINFO_CONTENT_SIGN, CMS_R_SIGNFINAL_ERROR);
605 OPENSSL_free(sig);
606 goto err;
607 }
608 ASN1_STRING_set0(si->signature, sig, siglen);
609 }
610
611 r = 1;
612
613 err:
614 EVP_MD_CTX_free(mctx);
615 EVP_PKEY_CTX_free(pctx);
616 return r;
617
618}
619
620int cms_SignedData_final(CMS_ContentInfo *cms, BIO *chain)
621{
622 STACK_OF(CMS_SignerInfo) *sinfos;
623 CMS_SignerInfo *si;
624 int i;
625 sinfos = CMS_get0_SignerInfos(cms);
626 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
627 si = sk_CMS_SignerInfo_value(sinfos, i);
628 if (!cms_SignerInfo_content_sign(cms, si, chain))
629 return 0;
630 }
631 cms->d.signedData->encapContentInfo->partial = 0;
632 return 1;
633}
634
635int CMS_SignerInfo_sign(CMS_SignerInfo *si)
636{
637 EVP_MD_CTX *mctx = si->mctx;
638 EVP_PKEY_CTX *pctx = NULL;
639 unsigned char *abuf = NULL;
640 int alen;
641 size_t siglen;
642 const EVP_MD *md = NULL;
643
644 md = EVP_get_digestbyobj(si->digestAlgorithm->algorithm);
645 if (md == NULL)
646 return 0;
647
648 if (CMS_signed_get_attr_by_NID(si, NID_pkcs9_signingTime, -1) < 0) {
649 if (!cms_add1_signingTime(si, NULL))
650 goto err;
651 }
652
653 if (si->pctx)
654 pctx = si->pctx;
655 else {
656 EVP_MD_CTX_reset(mctx);
657 if (EVP_DigestSignInit(mctx, &pctx, md, NULL, si->pkey) <= 0)
658 goto err;
659 si->pctx = pctx;
660 }
661
662 if (EVP_PKEY_CTX_ctrl(pctx, -1, EVP_PKEY_OP_SIGN,
663 EVP_PKEY_CTRL_CMS_SIGN, 0, si) <= 0) {
664 CMSerr(CMS_F_CMS_SIGNERINFO_SIGN, CMS_R_CTRL_ERROR);
665 goto err;
666 }
667
668 alen = ASN1_item_i2d((ASN1_VALUE *)si->signedAttrs, &abuf,
669 ASN1_ITEM_rptr(CMS_Attributes_Sign));
670 if (!abuf)
671 goto err;
672 if (EVP_DigestSignUpdate(mctx, abuf, alen) <= 0)
673 goto err;
674 if (EVP_DigestSignFinal(mctx, NULL, &siglen) <= 0)
675 goto err;
676 OPENSSL_free(abuf);
677 abuf = OPENSSL_malloc(siglen);
678 if (abuf == NULL)
679 goto err;
680 if (EVP_DigestSignFinal(mctx, abuf, &siglen) <= 0)
681 goto err;
682
683 if (EVP_PKEY_CTX_ctrl(pctx, -1, EVP_PKEY_OP_SIGN,
684 EVP_PKEY_CTRL_CMS_SIGN, 1, si) <= 0) {
685 CMSerr(CMS_F_CMS_SIGNERINFO_SIGN, CMS_R_CTRL_ERROR);
686 goto err;
687 }
688
689 EVP_MD_CTX_reset(mctx);
690
691 ASN1_STRING_set0(si->signature, abuf, siglen);
692
693 return 1;
694
695 err:
696 OPENSSL_free(abuf);
697 EVP_MD_CTX_reset(mctx);
698 return 0;
699
700}
701
702int CMS_SignerInfo_verify(CMS_SignerInfo *si)
703{
704 EVP_MD_CTX *mctx = NULL;
705 unsigned char *abuf = NULL;
706 int alen, r = -1;
707 const EVP_MD *md = NULL;
708
709 if (!si->pkey) {
710 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY, CMS_R_NO_PUBLIC_KEY);
711 return -1;
712 }
713
714 md = EVP_get_digestbyobj(si->digestAlgorithm->algorithm);
715 if (md == NULL)
716 return -1;
717 if (si->mctx == NULL && (si->mctx = EVP_MD_CTX_new()) == NULL) {
718 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY, ERR_R_MALLOC_FAILURE);
719 return -1;
720 }
721 mctx = si->mctx;
722 if (EVP_DigestVerifyInit(mctx, &si->pctx, md, NULL, si->pkey) <= 0)
723 goto err;
724
725 if (!cms_sd_asn1_ctrl(si, 1))
726 goto err;
727
728 alen = ASN1_item_i2d((ASN1_VALUE *)si->signedAttrs, &abuf,
729 ASN1_ITEM_rptr(CMS_Attributes_Verify));
730 if (!abuf)
731 goto err;
732 r = EVP_DigestVerifyUpdate(mctx, abuf, alen);
733 OPENSSL_free(abuf);
734 if (r <= 0) {
735 r = -1;
736 goto err;
737 }
738 r = EVP_DigestVerifyFinal(mctx,
739 si->signature->data, si->signature->length);
740 if (r <= 0)
741 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY, CMS_R_VERIFICATION_FAILURE);
742 err:
743 EVP_MD_CTX_reset(mctx);
744 return r;
745}
746
747/* Create a chain of digest BIOs from a CMS ContentInfo */
748
749BIO *cms_SignedData_init_bio(CMS_ContentInfo *cms)
750{
751 int i;
752 CMS_SignedData *sd;
753 BIO *chain = NULL;
754 sd = cms_get0_signed(cms);
755 if (!sd)
756 return NULL;
757 if (cms->d.signedData->encapContentInfo->partial)
758 cms_sd_set_version(sd);
759 for (i = 0; i < sk_X509_ALGOR_num(sd->digestAlgorithms); i++) {
760 X509_ALGOR *digestAlgorithm;
761 BIO *mdbio;
762 digestAlgorithm = sk_X509_ALGOR_value(sd->digestAlgorithms, i);
763 mdbio = cms_DigestAlgorithm_init_bio(digestAlgorithm);
764 if (!mdbio)
765 goto err;
766 if (chain)
767 BIO_push(chain, mdbio);
768 else
769 chain = mdbio;
770 }
771 return chain;
772 err:
773 BIO_free_all(chain);
774 return NULL;
775}
776
777int CMS_SignerInfo_verify_content(CMS_SignerInfo *si, BIO *chain)
778{
779 ASN1_OCTET_STRING *os = NULL;
780 EVP_MD_CTX *mctx = EVP_MD_CTX_new();
781 EVP_PKEY_CTX *pkctx = NULL;
782 int r = -1;
783 unsigned char mval[EVP_MAX_MD_SIZE];
784 unsigned int mlen;
785
786 if (mctx == NULL) {
787 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT, ERR_R_MALLOC_FAILURE);
788 goto err;
789 }
790 /* If we have any signed attributes look for messageDigest value */
791 if (CMS_signed_get_attr_count(si) >= 0) {
792 os = CMS_signed_get0_data_by_OBJ(si,
793 OBJ_nid2obj(NID_pkcs9_messageDigest),
794 -3, V_ASN1_OCTET_STRING);
795 if (!os) {
796 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT,
797 CMS_R_ERROR_READING_MESSAGEDIGEST_ATTRIBUTE);
798 goto err;
799 }
800 }
801
802 if (!cms_DigestAlgorithm_find_ctx(mctx, chain, si->digestAlgorithm))
803 goto err;
804
805 if (EVP_DigestFinal_ex(mctx, mval, &mlen) <= 0) {
806 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT,
807 CMS_R_UNABLE_TO_FINALIZE_CONTEXT);
808 goto err;
809 }
810
811 /* If messageDigest found compare it */
812
813 if (os) {
814 if (mlen != (unsigned int)os->length) {
815 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT,
816 CMS_R_MESSAGEDIGEST_ATTRIBUTE_WRONG_LENGTH);
817 goto err;
818 }
819
820 if (memcmp(mval, os->data, mlen)) {
821 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT,
822 CMS_R_VERIFICATION_FAILURE);
823 r = 0;
824 } else
825 r = 1;
826 } else {
827 const EVP_MD *md = EVP_MD_CTX_md(mctx);
828 pkctx = EVP_PKEY_CTX_new(si->pkey, NULL);
829 if (pkctx == NULL)
830 goto err;
831 if (EVP_PKEY_verify_init(pkctx) <= 0)
832 goto err;
833 if (EVP_PKEY_CTX_set_signature_md(pkctx, md) <= 0)
834 goto err;
835 si->pctx = pkctx;
836 if (!cms_sd_asn1_ctrl(si, 1))
837 goto err;
838 r = EVP_PKEY_verify(pkctx, si->signature->data,
839 si->signature->length, mval, mlen);
840 if (r <= 0) {
841 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CONTENT,
842 CMS_R_VERIFICATION_FAILURE);
843 r = 0;
844 }
845 }
846
847 err:
848 EVP_PKEY_CTX_free(pkctx);
849 EVP_MD_CTX_free(mctx);
850 return r;
851
852}
853
854int CMS_add_smimecap(CMS_SignerInfo *si, STACK_OF(X509_ALGOR) *algs)
855{
856 unsigned char *smder = NULL;
857 int smderlen, r;
858 smderlen = i2d_X509_ALGORS(algs, &smder);
859 if (smderlen <= 0)
860 return 0;
861 r = CMS_signed_add1_attr_by_NID(si, NID_SMIMECapabilities,
862 V_ASN1_SEQUENCE, smder, smderlen);
863 OPENSSL_free(smder);
864 return r;
865}
866
867int CMS_add_simple_smimecap(STACK_OF(X509_ALGOR) **algs,
868 int algnid, int keysize)
869{
870 X509_ALGOR *alg;
871 ASN1_INTEGER *key = NULL;
872 if (keysize > 0) {
873 key = ASN1_INTEGER_new();
874 if (key == NULL || !ASN1_INTEGER_set(key, keysize))
875 return 0;
876 }
877 alg = X509_ALGOR_new();
878 if (alg == NULL) {
879 ASN1_INTEGER_free(key);
880 return 0;
881 }
882
883 X509_ALGOR_set0(alg, OBJ_nid2obj(algnid),
884 key ? V_ASN1_INTEGER : V_ASN1_UNDEF, key);
885 if (*algs == NULL)
886 *algs = sk_X509_ALGOR_new_null();
887 if (*algs == NULL || !sk_X509_ALGOR_push(*algs, alg)) {
888 X509_ALGOR_free(alg);
889 return 0;
890 }
891 return 1;
892}
893
894/* Check to see if a cipher exists and if so add S/MIME capabilities */
895
896static int cms_add_cipher_smcap(STACK_OF(X509_ALGOR) **sk, int nid, int arg)
897{
898 if (EVP_get_cipherbynid(nid))
899 return CMS_add_simple_smimecap(sk, nid, arg);
900 return 1;
901}
902
903static int cms_add_digest_smcap(STACK_OF(X509_ALGOR) **sk, int nid, int arg)
904{
905 if (EVP_get_digestbynid(nid))
906 return CMS_add_simple_smimecap(sk, nid, arg);
907 return 1;
908}
909
910int CMS_add_standard_smimecap(STACK_OF(X509_ALGOR) **smcap)
911{
912 if (!cms_add_cipher_smcap(smcap, NID_aes_256_cbc, -1)
913 || !cms_add_digest_smcap(smcap, NID_id_GostR3411_2012_256, -1)
914 || !cms_add_digest_smcap(smcap, NID_id_GostR3411_2012_512, -1)
915 || !cms_add_digest_smcap(smcap, NID_id_GostR3411_94, -1)
916 || !cms_add_cipher_smcap(smcap, NID_id_Gost28147_89, -1)
917 || !cms_add_cipher_smcap(smcap, NID_aes_192_cbc, -1)
918 || !cms_add_cipher_smcap(smcap, NID_aes_128_cbc, -1)
919 || !cms_add_cipher_smcap(smcap, NID_des_ede3_cbc, -1)
920 || !cms_add_cipher_smcap(smcap, NID_rc2_cbc, 128)
921 || !cms_add_cipher_smcap(smcap, NID_rc2_cbc, 64)
922 || !cms_add_cipher_smcap(smcap, NID_des_cbc, -1)
923 || !cms_add_cipher_smcap(smcap, NID_rc2_cbc, 40))
924 return 0;
925 return 1;
926}
diff --git a/src/lib/libcrypto/cms/cms_smime.c b/src/lib/libcrypto/cms/cms_smime.c
new file mode 100644
index 0000000000..5dcf803f4b
--- /dev/null
+++ b/src/lib/libcrypto/cms/cms_smime.c
@@ -0,0 +1,843 @@
1/*
2 * Copyright 2008-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10#include "internal/cryptlib.h"
11#include <openssl/asn1t.h>
12#include <openssl/x509.h>
13#include <openssl/x509v3.h>
14#include <openssl/err.h>
15#include <openssl/cms.h>
16#include "cms_lcl.h"
17#include "internal/asn1_int.h"
18
19static BIO *cms_get_text_bio(BIO *out, unsigned int flags)
20{
21 BIO *rbio;
22 if (out == NULL)
23 rbio = BIO_new(BIO_s_null());
24 else if (flags & CMS_TEXT) {
25 rbio = BIO_new(BIO_s_mem());
26 BIO_set_mem_eof_return(rbio, 0);
27 } else
28 rbio = out;
29 return rbio;
30}
31
32static int cms_copy_content(BIO *out, BIO *in, unsigned int flags)
33{
34 unsigned char buf[4096];
35 int r = 0, i;
36 BIO *tmpout;
37
38 tmpout = cms_get_text_bio(out, flags);
39
40 if (tmpout == NULL) {
41 CMSerr(CMS_F_CMS_COPY_CONTENT, ERR_R_MALLOC_FAILURE);
42 goto err;
43 }
44
45 /* Read all content through chain to process digest, decrypt etc */
46 for (;;) {
47 i = BIO_read(in, buf, sizeof(buf));
48 if (i <= 0) {
49 if (BIO_method_type(in) == BIO_TYPE_CIPHER) {
50 if (!BIO_get_cipher_status(in))
51 goto err;
52 }
53 if (i < 0)
54 goto err;
55 break;
56 }
57
58 if (tmpout && (BIO_write(tmpout, buf, i) != i))
59 goto err;
60 }
61
62 if (flags & CMS_TEXT) {
63 if (!SMIME_text(tmpout, out)) {
64 CMSerr(CMS_F_CMS_COPY_CONTENT, CMS_R_SMIME_TEXT_ERROR);
65 goto err;
66 }
67 }
68
69 r = 1;
70
71 err:
72 if (tmpout != out)
73 BIO_free(tmpout);
74 return r;
75
76}
77
78static int check_content(CMS_ContentInfo *cms)
79{
80 ASN1_OCTET_STRING **pos = CMS_get0_content(cms);
81 if (!pos || !*pos) {
82 CMSerr(CMS_F_CHECK_CONTENT, CMS_R_NO_CONTENT);
83 return 0;
84 }
85 return 1;
86}
87
88static void do_free_upto(BIO *f, BIO *upto)
89{
90 if (upto) {
91 BIO *tbio;
92 do {
93 tbio = BIO_pop(f);
94 BIO_free(f);
95 f = tbio;
96 }
97 while (f && f != upto);
98 } else
99 BIO_free_all(f);
100}
101
102int CMS_data(CMS_ContentInfo *cms, BIO *out, unsigned int flags)
103{
104 BIO *cont;
105 int r;
106 if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_data) {
107 CMSerr(CMS_F_CMS_DATA, CMS_R_TYPE_NOT_DATA);
108 return 0;
109 }
110 cont = CMS_dataInit(cms, NULL);
111 if (!cont)
112 return 0;
113 r = cms_copy_content(out, cont, flags);
114 BIO_free_all(cont);
115 return r;
116}
117
118CMS_ContentInfo *CMS_data_create(BIO *in, unsigned int flags)
119{
120 CMS_ContentInfo *cms;
121 cms = cms_Data_create();
122 if (!cms)
123 return NULL;
124
125 if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
126 return cms;
127
128 CMS_ContentInfo_free(cms);
129
130 return NULL;
131}
132
133int CMS_digest_verify(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
134 unsigned int flags)
135{
136 BIO *cont;
137 int r;
138 if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_digest) {
139 CMSerr(CMS_F_CMS_DIGEST_VERIFY, CMS_R_TYPE_NOT_DIGESTED_DATA);
140 return 0;
141 }
142
143 if (!dcont && !check_content(cms))
144 return 0;
145
146 cont = CMS_dataInit(cms, dcont);
147 if (!cont)
148 return 0;
149 r = cms_copy_content(out, cont, flags);
150 if (r)
151 r = cms_DigestedData_do_final(cms, cont, 1);
152 do_free_upto(cont, dcont);
153 return r;
154}
155
156CMS_ContentInfo *CMS_digest_create(BIO *in, const EVP_MD *md,
157 unsigned int flags)
158{
159 CMS_ContentInfo *cms;
160 if (!md)
161 md = EVP_sha1();
162 cms = cms_DigestedData_create(md);
163 if (!cms)
164 return NULL;
165
166 if (!(flags & CMS_DETACHED))
167 CMS_set_detached(cms, 0);
168
169 if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
170 return cms;
171
172 CMS_ContentInfo_free(cms);
173 return NULL;
174}
175
176int CMS_EncryptedData_decrypt(CMS_ContentInfo *cms,
177 const unsigned char *key, size_t keylen,
178 BIO *dcont, BIO *out, unsigned int flags)
179{
180 BIO *cont;
181 int r;
182 if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_encrypted) {
183 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_DECRYPT,
184 CMS_R_TYPE_NOT_ENCRYPTED_DATA);
185 return 0;
186 }
187
188 if (!dcont && !check_content(cms))
189 return 0;
190
191 if (CMS_EncryptedData_set1_key(cms, NULL, key, keylen) <= 0)
192 return 0;
193 cont = CMS_dataInit(cms, dcont);
194 if (!cont)
195 return 0;
196 r = cms_copy_content(out, cont, flags);
197 do_free_upto(cont, dcont);
198 return r;
199}
200
201CMS_ContentInfo *CMS_EncryptedData_encrypt(BIO *in, const EVP_CIPHER *cipher,
202 const unsigned char *key,
203 size_t keylen, unsigned int flags)
204{
205 CMS_ContentInfo *cms;
206 if (!cipher) {
207 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_ENCRYPT, CMS_R_NO_CIPHER);
208 return NULL;
209 }
210 cms = CMS_ContentInfo_new();
211 if (cms == NULL)
212 return NULL;
213 if (!CMS_EncryptedData_set1_key(cms, cipher, key, keylen))
214 return NULL;
215
216 if (!(flags & CMS_DETACHED))
217 CMS_set_detached(cms, 0);
218
219 if ((flags & (CMS_STREAM | CMS_PARTIAL))
220 || CMS_final(cms, in, NULL, flags))
221 return cms;
222
223 CMS_ContentInfo_free(cms);
224 return NULL;
225}
226
227static int cms_signerinfo_verify_cert(CMS_SignerInfo *si,
228 X509_STORE *store,
229 STACK_OF(X509) *certs,
230 STACK_OF(X509_CRL) *crls)
231{
232 X509_STORE_CTX *ctx = X509_STORE_CTX_new();
233 X509 *signer;
234 int i, j, r = 0;
235
236 if (ctx == NULL) {
237 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT, ERR_R_MALLOC_FAILURE);
238 goto err;
239 }
240 CMS_SignerInfo_get0_algs(si, NULL, &signer, NULL, NULL);
241 if (!X509_STORE_CTX_init(ctx, store, signer, certs)) {
242 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT, CMS_R_STORE_INIT_ERROR);
243 goto err;
244 }
245 X509_STORE_CTX_set_default(ctx, "smime_sign");
246 if (crls)
247 X509_STORE_CTX_set0_crls(ctx, crls);
248
249 i = X509_verify_cert(ctx);
250 if (i <= 0) {
251 j = X509_STORE_CTX_get_error(ctx);
252 CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT,
253 CMS_R_CERTIFICATE_VERIFY_ERROR);
254 ERR_add_error_data(2, "Verify error:",
255 X509_verify_cert_error_string(j));
256 goto err;
257 }
258 r = 1;
259 err:
260 X509_STORE_CTX_free(ctx);
261 return r;
262
263}
264
265int CMS_verify(CMS_ContentInfo *cms, STACK_OF(X509) *certs,
266 X509_STORE *store, BIO *dcont, BIO *out, unsigned int flags)
267{
268 CMS_SignerInfo *si;
269 STACK_OF(CMS_SignerInfo) *sinfos;
270 STACK_OF(X509) *cms_certs = NULL;
271 STACK_OF(X509_CRL) *crls = NULL;
272 X509 *signer;
273 int i, scount = 0, ret = 0;
274 BIO *cmsbio = NULL, *tmpin = NULL, *tmpout = NULL;
275
276 if (!dcont && !check_content(cms))
277 return 0;
278 if (dcont && !(flags & CMS_BINARY)) {
279 const ASN1_OBJECT *coid = CMS_get0_eContentType(cms);
280 if (OBJ_obj2nid(coid) == NID_id_ct_asciiTextWithCRLF)
281 flags |= CMS_ASCIICRLF;
282 }
283
284 /* Attempt to find all signer certificates */
285
286 sinfos = CMS_get0_SignerInfos(cms);
287
288 if (sk_CMS_SignerInfo_num(sinfos) <= 0) {
289 CMSerr(CMS_F_CMS_VERIFY, CMS_R_NO_SIGNERS);
290 goto err;
291 }
292
293 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
294 si = sk_CMS_SignerInfo_value(sinfos, i);
295 CMS_SignerInfo_get0_algs(si, NULL, &signer, NULL, NULL);
296 if (signer)
297 scount++;
298 }
299
300 if (scount != sk_CMS_SignerInfo_num(sinfos))
301 scount += CMS_set1_signers_certs(cms, certs, flags);
302
303 if (scount != sk_CMS_SignerInfo_num(sinfos)) {
304 CMSerr(CMS_F_CMS_VERIFY, CMS_R_SIGNER_CERTIFICATE_NOT_FOUND);
305 goto err;
306 }
307
308 /* Attempt to verify all signers certs */
309
310 if (!(flags & CMS_NO_SIGNER_CERT_VERIFY)) {
311 cms_certs = CMS_get1_certs(cms);
312 if (!(flags & CMS_NOCRL))
313 crls = CMS_get1_crls(cms);
314 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
315 si = sk_CMS_SignerInfo_value(sinfos, i);
316 if (!cms_signerinfo_verify_cert(si, store, cms_certs, crls))
317 goto err;
318 }
319 }
320
321 /* Attempt to verify all SignerInfo signed attribute signatures */
322
323 if (!(flags & CMS_NO_ATTR_VERIFY)) {
324 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
325 si = sk_CMS_SignerInfo_value(sinfos, i);
326 if (CMS_signed_get_attr_count(si) < 0)
327 continue;
328 if (CMS_SignerInfo_verify(si) <= 0)
329 goto err;
330 }
331 }
332
333 /*
334 * Performance optimization: if the content is a memory BIO then store
335 * its contents in a temporary read only memory BIO. This avoids
336 * potentially large numbers of slow copies of data which will occur when
337 * reading from a read write memory BIO when signatures are calculated.
338 */
339
340 if (dcont && (BIO_method_type(dcont) == BIO_TYPE_MEM)) {
341 char *ptr;
342 long len;
343 len = BIO_get_mem_data(dcont, &ptr);
344 tmpin = BIO_new_mem_buf(ptr, len);
345 if (tmpin == NULL) {
346 CMSerr(CMS_F_CMS_VERIFY, ERR_R_MALLOC_FAILURE);
347 goto err2;
348 }
349 } else
350 tmpin = dcont;
351 /*
352 * If not binary mode and detached generate digests by *writing* through
353 * the BIO. That makes it possible to canonicalise the input.
354 */
355 if (!(flags & SMIME_BINARY) && dcont) {
356 /*
357 * Create output BIO so we can either handle text or to ensure
358 * included content doesn't override detached content.
359 */
360 tmpout = cms_get_text_bio(out, flags);
361 if (!tmpout) {
362 CMSerr(CMS_F_CMS_VERIFY, ERR_R_MALLOC_FAILURE);
363 goto err;
364 }
365 cmsbio = CMS_dataInit(cms, tmpout);
366 if (!cmsbio)
367 goto err;
368 /*
369 * Don't use SMIME_TEXT for verify: it adds headers and we want to
370 * remove them.
371 */
372 SMIME_crlf_copy(dcont, cmsbio, flags & ~SMIME_TEXT);
373
374 if (flags & CMS_TEXT) {
375 if (!SMIME_text(tmpout, out)) {
376 CMSerr(CMS_F_CMS_VERIFY, CMS_R_SMIME_TEXT_ERROR);
377 goto err;
378 }
379 }
380 } else {
381 cmsbio = CMS_dataInit(cms, tmpin);
382 if (!cmsbio)
383 goto err;
384
385 if (!cms_copy_content(out, cmsbio, flags))
386 goto err;
387
388 }
389 if (!(flags & CMS_NO_CONTENT_VERIFY)) {
390 for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
391 si = sk_CMS_SignerInfo_value(sinfos, i);
392 if (CMS_SignerInfo_verify_content(si, cmsbio) <= 0) {
393 CMSerr(CMS_F_CMS_VERIFY, CMS_R_CONTENT_VERIFY_ERROR);
394 goto err;
395 }
396 }
397 }
398
399 ret = 1;
400
401 err:
402 if (!(flags & SMIME_BINARY) && dcont) {
403 do_free_upto(cmsbio, tmpout);
404 if (tmpin != dcont)
405 BIO_free(tmpin);
406 } else {
407 if (dcont && (tmpin == dcont))
408 do_free_upto(cmsbio, dcont);
409 else
410 BIO_free_all(cmsbio);
411 }
412
413 if (out != tmpout)
414 BIO_free_all(tmpout);
415
416 err2:
417 sk_X509_pop_free(cms_certs, X509_free);
418 sk_X509_CRL_pop_free(crls, X509_CRL_free);
419
420 return ret;
421}
422
423int CMS_verify_receipt(CMS_ContentInfo *rcms, CMS_ContentInfo *ocms,
424 STACK_OF(X509) *certs,
425 X509_STORE *store, unsigned int flags)
426{
427 int r;
428 flags &= ~(CMS_DETACHED | CMS_TEXT);
429 r = CMS_verify(rcms, certs, store, NULL, NULL, flags);
430 if (r <= 0)
431 return r;
432 return cms_Receipt_verify(rcms, ocms);
433}
434
435CMS_ContentInfo *CMS_sign(X509 *signcert, EVP_PKEY *pkey,
436 STACK_OF(X509) *certs, BIO *data,
437 unsigned int flags)
438{
439 CMS_ContentInfo *cms;
440 int i;
441
442 cms = CMS_ContentInfo_new();
443 if (cms == NULL || !CMS_SignedData_init(cms))
444 goto merr;
445 if (flags & CMS_ASCIICRLF
446 && !CMS_set1_eContentType(cms,
447 OBJ_nid2obj(NID_id_ct_asciiTextWithCRLF)))
448 goto err;
449
450 if (pkey && !CMS_add1_signer(cms, signcert, pkey, NULL, flags)) {
451 CMSerr(CMS_F_CMS_SIGN, CMS_R_ADD_SIGNER_ERROR);
452 goto err;
453 }
454
455 for (i = 0; i < sk_X509_num(certs); i++) {
456 X509 *x = sk_X509_value(certs, i);
457 if (!CMS_add1_cert(cms, x))
458 goto merr;
459 }
460
461 if (!(flags & CMS_DETACHED))
462 CMS_set_detached(cms, 0);
463
464 if ((flags & (CMS_STREAM | CMS_PARTIAL))
465 || CMS_final(cms, data, NULL, flags))
466 return cms;
467 else
468 goto err;
469
470 merr:
471 CMSerr(CMS_F_CMS_SIGN, ERR_R_MALLOC_FAILURE);
472
473 err:
474 CMS_ContentInfo_free(cms);
475 return NULL;
476}
477
478CMS_ContentInfo *CMS_sign_receipt(CMS_SignerInfo *si,
479 X509 *signcert, EVP_PKEY *pkey,
480 STACK_OF(X509) *certs, unsigned int flags)
481{
482 CMS_SignerInfo *rct_si;
483 CMS_ContentInfo *cms = NULL;
484 ASN1_OCTET_STRING **pos, *os;
485 BIO *rct_cont = NULL;
486 int r = 0;
487
488 flags &= ~(CMS_STREAM | CMS_TEXT);
489 /* Not really detached but avoids content being allocated */
490 flags |= CMS_PARTIAL | CMS_BINARY | CMS_DETACHED;
491 if (!pkey || !signcert) {
492 CMSerr(CMS_F_CMS_SIGN_RECEIPT, CMS_R_NO_KEY_OR_CERT);
493 return NULL;
494 }
495
496 /* Initialize signed data */
497
498 cms = CMS_sign(NULL, NULL, certs, NULL, flags);
499 if (!cms)
500 goto err;
501
502 /* Set inner content type to signed receipt */
503 if (!CMS_set1_eContentType(cms, OBJ_nid2obj(NID_id_smime_ct_receipt)))
504 goto err;
505
506 rct_si = CMS_add1_signer(cms, signcert, pkey, NULL, flags);
507 if (!rct_si) {
508 CMSerr(CMS_F_CMS_SIGN_RECEIPT, CMS_R_ADD_SIGNER_ERROR);
509 goto err;
510 }
511
512 os = cms_encode_Receipt(si);
513
514 if (!os)
515 goto err;
516
517 /* Set content to digest */
518 rct_cont = BIO_new_mem_buf(os->data, os->length);
519 if (!rct_cont)
520 goto err;
521
522 /* Add msgSigDigest attribute */
523
524 if (!cms_msgSigDigest_add1(rct_si, si))
525 goto err;
526
527 /* Finalize structure */
528 if (!CMS_final(cms, rct_cont, NULL, flags))
529 goto err;
530
531 /* Set embedded content */
532 pos = CMS_get0_content(cms);
533 *pos = os;
534
535 r = 1;
536
537 err:
538 BIO_free(rct_cont);
539 if (r)
540 return cms;
541 CMS_ContentInfo_free(cms);
542 return NULL;
543
544}
545
546CMS_ContentInfo *CMS_encrypt(STACK_OF(X509) *certs, BIO *data,
547 const EVP_CIPHER *cipher, unsigned int flags)
548{
549 CMS_ContentInfo *cms;
550 int i;
551 X509 *recip;
552 cms = CMS_EnvelopedData_create(cipher);
553 if (!cms)
554 goto merr;
555 for (i = 0; i < sk_X509_num(certs); i++) {
556 recip = sk_X509_value(certs, i);
557 if (!CMS_add1_recipient_cert(cms, recip, flags)) {
558 CMSerr(CMS_F_CMS_ENCRYPT, CMS_R_RECIPIENT_ERROR);
559 goto err;
560 }
561 }
562
563 if (!(flags & CMS_DETACHED))
564 CMS_set_detached(cms, 0);
565
566 if ((flags & (CMS_STREAM | CMS_PARTIAL))
567 || CMS_final(cms, data, NULL, flags))
568 return cms;
569 else
570 goto err;
571
572 merr:
573 CMSerr(CMS_F_CMS_ENCRYPT, ERR_R_MALLOC_FAILURE);
574 err:
575 CMS_ContentInfo_free(cms);
576 return NULL;
577}
578
579static int cms_kari_set1_pkey(CMS_ContentInfo *cms, CMS_RecipientInfo *ri,
580 EVP_PKEY *pk, X509 *cert)
581{
582 int i;
583 STACK_OF(CMS_RecipientEncryptedKey) *reks;
584 CMS_RecipientEncryptedKey *rek;
585 reks = CMS_RecipientInfo_kari_get0_reks(ri);
586 for (i = 0; i < sk_CMS_RecipientEncryptedKey_num(reks); i++) {
587 int rv;
588 rek = sk_CMS_RecipientEncryptedKey_value(reks, i);
589 if (cert != NULL && CMS_RecipientEncryptedKey_cert_cmp(rek, cert))
590 continue;
591 CMS_RecipientInfo_kari_set0_pkey(ri, pk);
592 rv = CMS_RecipientInfo_kari_decrypt(cms, ri, rek);
593 CMS_RecipientInfo_kari_set0_pkey(ri, NULL);
594 if (rv > 0)
595 return 1;
596 return cert == NULL ? 0 : -1;
597 }
598 return 0;
599}
600
601int CMS_decrypt_set1_pkey(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert)
602{
603 STACK_OF(CMS_RecipientInfo) *ris;
604 CMS_RecipientInfo *ri;
605 int i, r, ri_type;
606 int debug = 0, match_ri = 0;
607 ris = CMS_get0_RecipientInfos(cms);
608 if (ris)
609 debug = cms->d.envelopedData->encryptedContentInfo->debug;
610 ri_type = cms_pkey_get_ri_type(pk);
611 if (ri_type == CMS_RECIPINFO_NONE) {
612 CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY,
613 CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
614 return 0;
615 }
616
617 for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
618 ri = sk_CMS_RecipientInfo_value(ris, i);
619 if (CMS_RecipientInfo_type(ri) != ri_type)
620 continue;
621 match_ri = 1;
622 if (ri_type == CMS_RECIPINFO_AGREE) {
623 r = cms_kari_set1_pkey(cms, ri, pk, cert);
624 if (r > 0)
625 return 1;
626 if (r < 0)
627 return 0;
628 }
629 /*
630 * If we have a cert try matching RecipientInfo otherwise try them
631 * all.
632 */
633 else if (!cert || !CMS_RecipientInfo_ktri_cert_cmp(ri, cert)) {
634 EVP_PKEY_up_ref(pk);
635 CMS_RecipientInfo_set0_pkey(ri, pk);
636 r = CMS_RecipientInfo_decrypt(cms, ri);
637 CMS_RecipientInfo_set0_pkey(ri, NULL);
638 if (cert) {
639 /*
640 * If not debugging clear any error and return success to
641 * avoid leaking of information useful to MMA
642 */
643 if (!debug) {
644 ERR_clear_error();
645 return 1;
646 }
647 if (r > 0)
648 return 1;
649 CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY, CMS_R_DECRYPT_ERROR);
650 return 0;
651 }
652 /*
653 * If no cert and not debugging don't leave loop after first
654 * successful decrypt. Always attempt to decrypt all recipients
655 * to avoid leaking timing of a successful decrypt.
656 */
657 else if (r > 0 && debug)
658 return 1;
659 }
660 }
661 /* If no cert, key transport and not debugging always return success */
662 if (cert == NULL && ri_type == CMS_RECIPINFO_TRANS && match_ri && !debug) {
663 ERR_clear_error();
664 return 1;
665 }
666
667 CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY, CMS_R_NO_MATCHING_RECIPIENT);
668 return 0;
669
670}
671
672int CMS_decrypt_set1_key(CMS_ContentInfo *cms,
673 unsigned char *key, size_t keylen,
674 const unsigned char *id, size_t idlen)
675{
676 STACK_OF(CMS_RecipientInfo) *ris;
677 CMS_RecipientInfo *ri;
678 int i, r;
679 ris = CMS_get0_RecipientInfos(cms);
680 for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
681 ri = sk_CMS_RecipientInfo_value(ris, i);
682 if (CMS_RecipientInfo_type(ri) != CMS_RECIPINFO_KEK)
683 continue;
684
685 /*
686 * If we have an id try matching RecipientInfo otherwise try them
687 * all.
688 */
689 if (!id || (CMS_RecipientInfo_kekri_id_cmp(ri, id, idlen) == 0)) {
690 CMS_RecipientInfo_set0_key(ri, key, keylen);
691 r = CMS_RecipientInfo_decrypt(cms, ri);
692 CMS_RecipientInfo_set0_key(ri, NULL, 0);
693 if (r > 0)
694 return 1;
695 if (id) {
696 CMSerr(CMS_F_CMS_DECRYPT_SET1_KEY, CMS_R_DECRYPT_ERROR);
697 return 0;
698 }
699 ERR_clear_error();
700 }
701 }
702
703 CMSerr(CMS_F_CMS_DECRYPT_SET1_KEY, CMS_R_NO_MATCHING_RECIPIENT);
704 return 0;
705
706}
707
708int CMS_decrypt_set1_password(CMS_ContentInfo *cms,
709 unsigned char *pass, ossl_ssize_t passlen)
710{
711 STACK_OF(CMS_RecipientInfo) *ris;
712 CMS_RecipientInfo *ri;
713 int i, r;
714 ris = CMS_get0_RecipientInfos(cms);
715 for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
716 ri = sk_CMS_RecipientInfo_value(ris, i);
717 if (CMS_RecipientInfo_type(ri) != CMS_RECIPINFO_PASS)
718 continue;
719 CMS_RecipientInfo_set0_password(ri, pass, passlen);
720 r = CMS_RecipientInfo_decrypt(cms, ri);
721 CMS_RecipientInfo_set0_password(ri, NULL, 0);
722 if (r > 0)
723 return 1;
724 }
725
726 CMSerr(CMS_F_CMS_DECRYPT_SET1_PASSWORD, CMS_R_NO_MATCHING_RECIPIENT);
727 return 0;
728
729}
730
731int CMS_decrypt(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert,
732 BIO *dcont, BIO *out, unsigned int flags)
733{
734 int r;
735 BIO *cont;
736 if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_enveloped) {
737 CMSerr(CMS_F_CMS_DECRYPT, CMS_R_TYPE_NOT_ENVELOPED_DATA);
738 return 0;
739 }
740 if (!dcont && !check_content(cms))
741 return 0;
742 if (flags & CMS_DEBUG_DECRYPT)
743 cms->d.envelopedData->encryptedContentInfo->debug = 1;
744 else
745 cms->d.envelopedData->encryptedContentInfo->debug = 0;
746 if (!pk && !cert && !dcont && !out)
747 return 1;
748 if (pk && !CMS_decrypt_set1_pkey(cms, pk, cert))
749 return 0;
750 cont = CMS_dataInit(cms, dcont);
751 if (!cont)
752 return 0;
753 r = cms_copy_content(out, cont, flags);
754 do_free_upto(cont, dcont);
755 return r;
756}
757
758int CMS_final(CMS_ContentInfo *cms, BIO *data, BIO *dcont, unsigned int flags)
759{
760 BIO *cmsbio;
761 int ret = 0;
762
763 if ((cmsbio = CMS_dataInit(cms, dcont)) == NULL) {
764 CMSerr(CMS_F_CMS_FINAL, CMS_R_CMS_LIB);
765 return 0;
766 }
767
768 SMIME_crlf_copy(data, cmsbio, flags);
769
770 (void)BIO_flush(cmsbio);
771
772 if (!CMS_dataFinal(cms, cmsbio)) {
773 CMSerr(CMS_F_CMS_FINAL, CMS_R_CMS_DATAFINAL_ERROR);
774 goto err;
775 }
776
777 ret = 1;
778
779 err:
780 do_free_upto(cmsbio, dcont);
781
782 return ret;
783
784}
785
786#ifdef ZLIB
787
788int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
789 unsigned int flags)
790{
791 BIO *cont;
792 int r;
793 if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_id_smime_ct_compressedData) {
794 CMSerr(CMS_F_CMS_UNCOMPRESS, CMS_R_TYPE_NOT_COMPRESSED_DATA);
795 return 0;
796 }
797
798 if (!dcont && !check_content(cms))
799 return 0;
800
801 cont = CMS_dataInit(cms, dcont);
802 if (!cont)
803 return 0;
804 r = cms_copy_content(out, cont, flags);
805 do_free_upto(cont, dcont);
806 return r;
807}
808
809CMS_ContentInfo *CMS_compress(BIO *in, int comp_nid, unsigned int flags)
810{
811 CMS_ContentInfo *cms;
812 if (comp_nid <= 0)
813 comp_nid = NID_zlib_compression;
814 cms = cms_CompressedData_create(comp_nid);
815 if (!cms)
816 return NULL;
817
818 if (!(flags & CMS_DETACHED))
819 CMS_set_detached(cms, 0);
820
821 if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
822 return cms;
823
824 CMS_ContentInfo_free(cms);
825 return NULL;
826}
827
828#else
829
830int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
831 unsigned int flags)
832{
833 CMSerr(CMS_F_CMS_UNCOMPRESS, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
834 return 0;
835}
836
837CMS_ContentInfo *CMS_compress(BIO *in, int comp_nid, unsigned int flags)
838{
839 CMSerr(CMS_F_CMS_COMPRESS, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
840 return NULL;
841}
842
843#endif