summaryrefslogtreecommitdiff
path: root/src/lib/libcrypto/cms/cms_enc.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/libcrypto/cms/cms_enc.c')
-rw-r--r--src/lib/libcrypto/cms/cms_enc.c181
1 files changed, 77 insertions, 104 deletions
diff --git a/src/lib/libcrypto/cms/cms_enc.c b/src/lib/libcrypto/cms/cms_enc.c
index 612fce6dde..75e08cdb1d 100644
--- a/src/lib/libcrypto/cms/cms_enc.c
+++ b/src/lib/libcrypto/cms/cms_enc.c
@@ -10,7 +10,7 @@
10 * are met: 10 * are met:
11 * 11 *
12 * 1. Redistributions of source code must retain the above copyright 12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer. 13 * notice, this list of conditions and the following disclaimer.
14 * 14 *
15 * 2. Redistributions in binary form must reproduce the above copyright 15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in 16 * notice, this list of conditions and the following disclaimer in
@@ -66,8 +66,9 @@ DECLARE_ASN1_ITEM(CMS_EncryptedData)
66 66
67/* Return BIO based on EncryptedContentInfo and key */ 67/* Return BIO based on EncryptedContentInfo and key */
68 68
69BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec) 69BIO *
70 { 70cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec)
71{
71 BIO *b; 72 BIO *b;
72 EVP_CIPHER_CTX *ctx; 73 EVP_CIPHER_CTX *ctx;
73 const EVP_CIPHER *ciph; 74 const EVP_CIPHER *ciph;
@@ -75,87 +76,72 @@ BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec)
75 unsigned char iv[EVP_MAX_IV_LENGTH], *piv = NULL; 76 unsigned char iv[EVP_MAX_IV_LENGTH], *piv = NULL;
76 unsigned char *tkey = NULL; 77 unsigned char *tkey = NULL;
77 size_t tkeylen = 0; 78 size_t tkeylen = 0;
78
79 int ok = 0; 79 int ok = 0;
80
81 int enc, keep_key = 0; 80 int enc, keep_key = 0;
82 81
83 enc = ec->cipher ? 1 : 0; 82 enc = ec->cipher ? 1 : 0;
84 83
85 b = BIO_new(BIO_f_cipher()); 84 b = BIO_new(BIO_f_cipher());
86 if (!b) 85 if (!b) {
87 {
88 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 86 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
89 ERR_R_MALLOC_FAILURE); 87 ERR_R_MALLOC_FAILURE);
90 return NULL; 88 return NULL;
91 } 89 }
92 90
93 BIO_get_cipher_ctx(b, &ctx); 91 BIO_get_cipher_ctx(b, &ctx);
94 92
95 if (enc) 93 if (enc) {
96 {
97 ciph = ec->cipher; 94 ciph = ec->cipher;
98 /* If not keeping key set cipher to NULL so subsequent calls 95 /* If not keeping key set cipher to NULL so subsequent calls
99 * decrypt. 96 * decrypt.
100 */ 97 */
101 if (ec->key) 98 if (ec->key)
102 ec->cipher = NULL; 99 ec->cipher = NULL;
103 } 100 } else {
104 else
105 {
106 ciph = EVP_get_cipherbyobj(calg->algorithm); 101 ciph = EVP_get_cipherbyobj(calg->algorithm);
107 102
108 if (!ciph) 103 if (!ciph) {
109 {
110 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 104 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
111 CMS_R_UNKNOWN_CIPHER); 105 CMS_R_UNKNOWN_CIPHER);
112 goto err; 106 goto err;
113 }
114 } 107 }
108 }
115 109
116 if (EVP_CipherInit_ex(ctx, ciph, NULL, NULL, NULL, enc) <= 0) 110 if (EVP_CipherInit_ex(ctx, ciph, NULL, NULL, NULL, enc) <= 0) {
117 {
118 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 111 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
119 CMS_R_CIPHER_INITIALISATION_ERROR); 112 CMS_R_CIPHER_INITIALISATION_ERROR);
120 goto err; 113 goto err;
121 } 114 }
122 115
123 if (enc) 116 if (enc) {
124 {
125 int ivlen; 117 int ivlen;
126 calg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_type(ctx)); 118 calg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_type(ctx));
127 /* Generate a random IV if we need one */ 119 /* Generate a random IV if we need one */
128 ivlen = EVP_CIPHER_CTX_iv_length(ctx); 120 ivlen = EVP_CIPHER_CTX_iv_length(ctx);
129 if (ivlen > 0) 121 if (ivlen > 0) {
130 {
131 if (RAND_pseudo_bytes(iv, ivlen) <= 0) 122 if (RAND_pseudo_bytes(iv, ivlen) <= 0)
132 goto err; 123 goto err;
133 piv = iv; 124 piv = iv;
134 }
135 } 125 }
136 else if (EVP_CIPHER_asn1_to_param(ctx, calg->parameter) <= 0) 126 } else if (EVP_CIPHER_asn1_to_param(ctx, calg->parameter) <= 0) {
137 {
138 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 127 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
139 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); 128 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
140 goto err; 129 goto err;
141 } 130 }
142 tkeylen = EVP_CIPHER_CTX_key_length(ctx); 131 tkeylen = EVP_CIPHER_CTX_key_length(ctx);
143 /* Generate random session key */ 132 /* Generate random session key */
144 if (!enc || !ec->key) 133 if (!enc || !ec->key) {
145 {
146 tkey = malloc(tkeylen); 134 tkey = malloc(tkeylen);
147 if (!tkey) 135 if (!tkey) {
148 {
149 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 136 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
150 ERR_R_MALLOC_FAILURE); 137 ERR_R_MALLOC_FAILURE);
151 goto err; 138 goto err;
152 } 139 }
153 if (EVP_CIPHER_CTX_rand_key(ctx, tkey) <= 0) 140 if (EVP_CIPHER_CTX_rand_key(ctx, tkey) <= 0)
154 goto err; 141 goto err;
155 } 142 }
156 143
157 if (!ec->key) 144 if (!ec->key) {
158 {
159 ec->key = tkey; 145 ec->key = tkey;
160 ec->keylen = tkeylen; 146 ec->keylen = tkeylen;
161 tkey = NULL; 147 tkey = NULL;
@@ -163,25 +149,20 @@ BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec)
163 keep_key = 1; 149 keep_key = 1;
164 else 150 else
165 ERR_clear_error(); 151 ERR_clear_error();
166
167 }
168 152
169 if (ec->keylen != tkeylen) 153 }
170 { 154
155 if (ec->keylen != tkeylen) {
171 /* If necessary set key length */ 156 /* If necessary set key length */
172 if (EVP_CIPHER_CTX_set_key_length(ctx, ec->keylen) <= 0) 157 if (EVP_CIPHER_CTX_set_key_length(ctx, ec->keylen) <= 0) {
173 {
174 /* Only reveal failure if debugging so we don't 158 /* Only reveal failure if debugging so we don't
175 * leak information which may be useful in MMA. 159 * leak information which may be useful in MMA.
176 */ 160 */
177 if (enc || ec->debug) 161 if (enc || ec->debug) {
178 {
179 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 162 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
180 CMS_R_INVALID_KEY_LENGTH); 163 CMS_R_INVALID_KEY_LENGTH);
181 goto err; 164 goto err;
182 } 165 } else {
183 else
184 {
185 /* Use random key */ 166 /* Use random key */
186 OPENSSL_cleanse(ec->key, ec->keylen); 167 OPENSSL_cleanse(ec->key, ec->keylen);
187 free(ec->key); 168 free(ec->key);
@@ -189,106 +170,98 @@ BIO *cms_EncryptedContent_init_bio(CMS_EncryptedContentInfo *ec)
189 ec->keylen = tkeylen; 170 ec->keylen = tkeylen;
190 tkey = NULL; 171 tkey = NULL;
191 ERR_clear_error(); 172 ERR_clear_error();
192 }
193 } 173 }
194 } 174 }
175 }
195 176
196 if (EVP_CipherInit_ex(ctx, NULL, NULL, ec->key, piv, enc) <= 0) 177 if (EVP_CipherInit_ex(ctx, NULL, NULL, ec->key, piv, enc) <= 0) {
197 {
198 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 178 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
199 CMS_R_CIPHER_INITIALISATION_ERROR); 179 CMS_R_CIPHER_INITIALISATION_ERROR);
200 goto err; 180 goto err;
201 } 181 }
202 182
203 if (piv) 183 if (piv) {
204 {
205 calg->parameter = ASN1_TYPE_new(); 184 calg->parameter = ASN1_TYPE_new();
206 if (!calg->parameter) 185 if (!calg->parameter) {
207 {
208 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 186 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
209 ERR_R_MALLOC_FAILURE); 187 ERR_R_MALLOC_FAILURE);
210 goto err; 188 goto err;
211 } 189 }
212 if (EVP_CIPHER_param_to_asn1(ctx, calg->parameter) <= 0) 190 if (EVP_CIPHER_param_to_asn1(ctx, calg->parameter) <= 0) {
213 {
214 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO, 191 CMSerr(CMS_F_CMS_ENCRYPTEDCONTENT_INIT_BIO,
215 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); 192 CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR);
216 goto err; 193 goto err;
217 }
218 } 194 }
195 }
219 ok = 1; 196 ok = 1;
220 197
221 err: 198err:
222 if (ec->key && !keep_key) 199 if (ec->key && !keep_key) {
223 {
224 OPENSSL_cleanse(ec->key, ec->keylen); 200 OPENSSL_cleanse(ec->key, ec->keylen);
225 free(ec->key); 201 free(ec->key);
226 ec->key = NULL; 202 ec->key = NULL;
227 } 203 }
228 if (tkey) 204 if (tkey) {
229 {
230 OPENSSL_cleanse(tkey, tkeylen); 205 OPENSSL_cleanse(tkey, tkeylen);
231 free(tkey); 206 free(tkey);
232 } 207 }
233 if (ok) 208 if (ok)
234 return b; 209 return b;
235 BIO_free(b); 210 BIO_free(b);
236 return NULL; 211 return NULL;
237 } 212}
238 213
239int cms_EncryptedContent_init(CMS_EncryptedContentInfo *ec, 214int
240 const EVP_CIPHER *cipher, 215cms_EncryptedContent_init(CMS_EncryptedContentInfo *ec,
241 const unsigned char *key, size_t keylen) 216 const EVP_CIPHER *cipher, const unsigned char *key, size_t keylen)
242 { 217{
243 ec->cipher = cipher; 218 ec->cipher = cipher;
244 if (key) 219 if (key) {
245 {
246 ec->key = malloc(keylen); 220 ec->key = malloc(keylen);
247 if (!ec->key) 221 if (!ec->key)
248 return 0; 222 return 0;
249 memcpy(ec->key, key, keylen); 223 memcpy(ec->key, key, keylen);
250 } 224 }
251 ec->keylen = keylen; 225 ec->keylen = keylen;
252 if (cipher) 226 if (cipher)
253 ec->contentType = OBJ_nid2obj(NID_pkcs7_data); 227 ec->contentType = OBJ_nid2obj(NID_pkcs7_data);
254 return 1; 228 return 1;
255 } 229}
256 230
257int CMS_EncryptedData_set1_key(CMS_ContentInfo *cms, const EVP_CIPHER *ciph, 231int
258 const unsigned char *key, size_t keylen) 232CMS_EncryptedData_set1_key(CMS_ContentInfo *cms, const EVP_CIPHER *ciph,
259 { 233 const unsigned char *key, size_t keylen)
234{
260 CMS_EncryptedContentInfo *ec; 235 CMS_EncryptedContentInfo *ec;
261 if (!key || !keylen) 236
262 { 237 if (!key || !keylen) {
263 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, CMS_R_NO_KEY); 238 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, CMS_R_NO_KEY);
264 return 0; 239 return 0;
265 } 240 }
266 if (ciph) 241 if (ciph) {
267 {
268 cms->d.encryptedData = M_ASN1_new_of(CMS_EncryptedData); 242 cms->d.encryptedData = M_ASN1_new_of(CMS_EncryptedData);
269 if (!cms->d.encryptedData) 243 if (!cms->d.encryptedData) {
270 {
271 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, 244 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY,
272 ERR_R_MALLOC_FAILURE); 245 ERR_R_MALLOC_FAILURE);
273 return 0; 246 return 0;
274 } 247 }
275 cms->contentType = OBJ_nid2obj(NID_pkcs7_encrypted); 248 cms->contentType = OBJ_nid2obj(NID_pkcs7_encrypted);
276 cms->d.encryptedData->version = 0; 249 cms->d.encryptedData->version = 0;
277 } 250 } else if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_encrypted) {
278 else if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_encrypted)
279 {
280 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY, 251 CMSerr(CMS_F_CMS_ENCRYPTEDDATA_SET1_KEY,
281 CMS_R_NOT_ENCRYPTED_DATA); 252 CMS_R_NOT_ENCRYPTED_DATA);
282 return 0; 253 return 0;
283 } 254 }
284 ec = cms->d.encryptedData->encryptedContentInfo; 255 ec = cms->d.encryptedData->encryptedContentInfo;
285 return cms_EncryptedContent_init(ec, ciph, key, keylen); 256 return cms_EncryptedContent_init(ec, ciph, key, keylen);
286 } 257}
287 258
288BIO *cms_EncryptedData_init_bio(CMS_ContentInfo *cms) 259BIO *
289 { 260cms_EncryptedData_init_bio(CMS_ContentInfo *cms)
261{
290 CMS_EncryptedData *enc = cms->d.encryptedData; 262 CMS_EncryptedData *enc = cms->d.encryptedData;
263
291 if (enc->encryptedContentInfo->cipher && enc->unprotectedAttrs) 264 if (enc->encryptedContentInfo->cipher && enc->unprotectedAttrs)
292 enc->version = 2; 265 enc->version = 2;
293 return cms_EncryptedContent_init_bio(enc->encryptedContentInfo); 266 return cms_EncryptedContent_init_bio(enc->encryptedContentInfo);
294 } 267}