xref: /aosp_15_r20/external/boringssl/src/crypto/fipsmodule/cipher/cipher.c (revision 8fb009dc861624b67b6cdb62ea21f0f22d0c584b)
1 /* Copyright (C) 1995-1998 Eric Young ([email protected])
2  * All rights reserved.
3  *
4  * This package is an SSL implementation written
5  * by Eric Young ([email protected]).
6  * The implementation was written so as to conform with Netscapes SSL.
7  *
8  * This library is free for commercial and non-commercial use as long as
9  * the following conditions are aheared to.  The following conditions
10  * apply to all code found in this distribution, be it the RC4, RSA,
11  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
12  * included with this distribution is covered by the same copyright terms
13  * except that the holder is Tim Hudson ([email protected]).
14  *
15  * Copyright remains Eric Young's, and as such any Copyright notices in
16  * the code are not to be removed.
17  * If this package is used in a product, Eric Young should be given attribution
18  * as the author of the parts of the library used.
19  * This can be in the form of a textual message at program startup or
20  * in documentation (online or textual) provided with the package.
21  *
22  * Redistribution and use in source and binary forms, with or without
23  * modification, are permitted provided that the following conditions
24  * are met:
25  * 1. Redistributions of source code must retain the copyright
26  *    notice, this list of conditions and the following disclaimer.
27  * 2. Redistributions in binary form must reproduce the above copyright
28  *    notice, this list of conditions and the following disclaimer in the
29  *    documentation and/or other materials provided with the distribution.
30  * 3. All advertising materials mentioning features or use of this software
31  *    must display the following acknowledgement:
32  *    "This product includes cryptographic software written by
33  *     Eric Young ([email protected])"
34  *    The word 'cryptographic' can be left out if the rouines from the library
35  *    being used are not cryptographic related :-).
36  * 4. If you include any Windows specific code (or a derivative thereof) from
37  *    the apps directory (application code) you must include an acknowledgement:
38  *    "This product includes software written by Tim Hudson ([email protected])"
39  *
40  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
41  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
43  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
44  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
45  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
46  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
47  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
48  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
49  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
50  * SUCH DAMAGE.
51  *
52  * The licence and distribution terms for any publically available version or
53  * derivative of this code cannot be changed.  i.e. this code cannot simply be
54  * copied and put under another distribution licence
55  * [including the GNU Public Licence.] */
56 
57 #include <openssl/cipher.h>
58 
59 #include <assert.h>
60 #include <limits.h>
61 #include <string.h>
62 
63 #include <openssl/err.h>
64 #include <openssl/mem.h>
65 #include <openssl/nid.h>
66 
67 #include "internal.h"
68 #include "../service_indicator/internal.h"
69 #include "../../internal.h"
70 
71 
EVP_CIPHER_CTX_init(EVP_CIPHER_CTX * ctx)72 void EVP_CIPHER_CTX_init(EVP_CIPHER_CTX *ctx) {
73   OPENSSL_memset(ctx, 0, sizeof(EVP_CIPHER_CTX));
74 }
75 
EVP_CIPHER_CTX_new(void)76 EVP_CIPHER_CTX *EVP_CIPHER_CTX_new(void) {
77   EVP_CIPHER_CTX *ctx = OPENSSL_malloc(sizeof(EVP_CIPHER_CTX));
78   if (ctx) {
79     EVP_CIPHER_CTX_init(ctx);
80   }
81   return ctx;
82 }
83 
EVP_CIPHER_CTX_cleanup(EVP_CIPHER_CTX * c)84 int EVP_CIPHER_CTX_cleanup(EVP_CIPHER_CTX *c) {
85   if (c->cipher != NULL && c->cipher->cleanup) {
86     c->cipher->cleanup(c);
87   }
88   OPENSSL_free(c->cipher_data);
89 
90   OPENSSL_memset(c, 0, sizeof(EVP_CIPHER_CTX));
91   return 1;
92 }
93 
EVP_CIPHER_CTX_free(EVP_CIPHER_CTX * ctx)94 void EVP_CIPHER_CTX_free(EVP_CIPHER_CTX *ctx) {
95   if (ctx) {
96     EVP_CIPHER_CTX_cleanup(ctx);
97     OPENSSL_free(ctx);
98   }
99 }
100 
EVP_CIPHER_CTX_copy(EVP_CIPHER_CTX * out,const EVP_CIPHER_CTX * in)101 int EVP_CIPHER_CTX_copy(EVP_CIPHER_CTX *out, const EVP_CIPHER_CTX *in) {
102   if (in == NULL || in->cipher == NULL) {
103     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_INPUT_NOT_INITIALIZED);
104     return 0;
105   }
106 
107   if (in->poisoned) {
108     OPENSSL_PUT_ERROR(CIPHER, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED);
109     return 0;
110   }
111 
112   EVP_CIPHER_CTX_cleanup(out);
113   OPENSSL_memcpy(out, in, sizeof(EVP_CIPHER_CTX));
114 
115   if (in->cipher_data && in->cipher->ctx_size) {
116     out->cipher_data = OPENSSL_memdup(in->cipher_data, in->cipher->ctx_size);
117     if (!out->cipher_data) {
118       out->cipher = NULL;
119       return 0;
120     }
121   }
122 
123   if (in->cipher->flags & EVP_CIPH_CUSTOM_COPY) {
124     if (!in->cipher->ctrl((EVP_CIPHER_CTX *)in, EVP_CTRL_COPY, 0, out)) {
125       out->cipher = NULL;
126       return 0;
127     }
128   }
129 
130   return 1;
131 }
132 
EVP_CIPHER_CTX_reset(EVP_CIPHER_CTX * ctx)133 int EVP_CIPHER_CTX_reset(EVP_CIPHER_CTX *ctx) {
134   EVP_CIPHER_CTX_cleanup(ctx);
135   EVP_CIPHER_CTX_init(ctx);
136   return 1;
137 }
138 
EVP_CipherInit_ex(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,ENGINE * engine,const uint8_t * key,const uint8_t * iv,int enc)139 int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
140                       ENGINE *engine, const uint8_t *key, const uint8_t *iv,
141                       int enc) {
142   if (enc == -1) {
143     enc = ctx->encrypt;
144   } else {
145     if (enc) {
146       enc = 1;
147     }
148     ctx->encrypt = enc;
149   }
150 
151   if (cipher) {
152     // Ensure a context left from last time is cleared (the previous check
153     // attempted to avoid this if the same ENGINE and EVP_CIPHER could be
154     // used).
155     if (ctx->cipher) {
156       EVP_CIPHER_CTX_cleanup(ctx);
157       // Restore encrypt and flags
158       ctx->encrypt = enc;
159     }
160 
161     ctx->cipher = cipher;
162     if (ctx->cipher->ctx_size) {
163       ctx->cipher_data = OPENSSL_malloc(ctx->cipher->ctx_size);
164       if (!ctx->cipher_data) {
165         ctx->cipher = NULL;
166         return 0;
167       }
168     } else {
169       ctx->cipher_data = NULL;
170     }
171 
172     ctx->key_len = cipher->key_len;
173     ctx->flags = 0;
174 
175     if (ctx->cipher->flags & EVP_CIPH_CTRL_INIT) {
176       if (!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_INIT, 0, NULL)) {
177         ctx->cipher = NULL;
178         OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_INITIALIZATION_ERROR);
179         return 0;
180       }
181     }
182   } else if (!ctx->cipher) {
183     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_NO_CIPHER_SET);
184     return 0;
185   }
186 
187   // we assume block size is a power of 2 in *cryptUpdate
188   assert(ctx->cipher->block_size == 1 || ctx->cipher->block_size == 8 ||
189          ctx->cipher->block_size == 16);
190 
191   if (!(EVP_CIPHER_CTX_flags(ctx) & EVP_CIPH_CUSTOM_IV)) {
192     switch (EVP_CIPHER_CTX_mode(ctx)) {
193       case EVP_CIPH_STREAM_CIPHER:
194       case EVP_CIPH_ECB_MODE:
195         break;
196 
197       case EVP_CIPH_CFB_MODE:
198         ctx->num = 0;
199         OPENSSL_FALLTHROUGH;
200 
201       case EVP_CIPH_CBC_MODE:
202         assert(EVP_CIPHER_CTX_iv_length(ctx) <= sizeof(ctx->iv));
203         if (iv) {
204           OPENSSL_memcpy(ctx->oiv, iv, EVP_CIPHER_CTX_iv_length(ctx));
205         }
206         OPENSSL_memcpy(ctx->iv, ctx->oiv, EVP_CIPHER_CTX_iv_length(ctx));
207         break;
208 
209       case EVP_CIPH_CTR_MODE:
210       case EVP_CIPH_OFB_MODE:
211         ctx->num = 0;
212         // Don't reuse IV for CTR mode
213         if (iv) {
214           OPENSSL_memcpy(ctx->iv, iv, EVP_CIPHER_CTX_iv_length(ctx));
215         }
216         break;
217 
218       default:
219         return 0;
220     }
221   }
222 
223   if (key || (ctx->cipher->flags & EVP_CIPH_ALWAYS_CALL_INIT)) {
224     if (!ctx->cipher->init(ctx, key, iv, enc)) {
225       return 0;
226     }
227   }
228 
229   ctx->buf_len = 0;
230   ctx->final_used = 0;
231   // Clear the poisoned flag to permit re-use of a CTX that previously had a
232   // failed operation.
233   ctx->poisoned = 0;
234   return 1;
235 }
236 
EVP_EncryptInit_ex(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,ENGINE * impl,const uint8_t * key,const uint8_t * iv)237 int EVP_EncryptInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
238                        ENGINE *impl, const uint8_t *key, const uint8_t *iv) {
239   return EVP_CipherInit_ex(ctx, cipher, impl, key, iv, 1);
240 }
241 
EVP_DecryptInit_ex(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,ENGINE * impl,const uint8_t * key,const uint8_t * iv)242 int EVP_DecryptInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
243                        ENGINE *impl, const uint8_t *key, const uint8_t *iv) {
244   return EVP_CipherInit_ex(ctx, cipher, impl, key, iv, 0);
245 }
246 
247 // block_remainder returns the number of bytes to remove from |len| to get a
248 // multiple of |ctx|'s block size.
block_remainder(const EVP_CIPHER_CTX * ctx,int len)249 static int block_remainder(const EVP_CIPHER_CTX *ctx, int len) {
250   // |block_size| must be a power of two.
251   assert(ctx->cipher->block_size != 0);
252   assert((ctx->cipher->block_size & (ctx->cipher->block_size - 1)) == 0);
253   return len & (ctx->cipher->block_size - 1);
254 }
255 
EVP_EncryptUpdate(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len,const uint8_t * in,int in_len)256 int EVP_EncryptUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len,
257                       const uint8_t *in, int in_len) {
258   if (ctx->poisoned) {
259     OPENSSL_PUT_ERROR(CIPHER, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED);
260     return 0;
261   }
262   // If the first call to |cipher| succeeds and the second fails, |ctx| may be
263   // left in an indeterminate state. We set a poison flag on failure to ensure
264   // callers do not continue to use the object in that case.
265   ctx->poisoned = 1;
266 
267   // Ciphers that use blocks may write up to |bl| extra bytes. Ensure the output
268   // does not overflow |*out_len|.
269   int bl = ctx->cipher->block_size;
270   if (bl > 1 && in_len > INT_MAX - bl) {
271     OPENSSL_PUT_ERROR(CIPHER, ERR_R_OVERFLOW);
272     return 0;
273   }
274 
275   if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
276     int ret = ctx->cipher->cipher(ctx, out, in, in_len);
277     if (ret < 0) {
278       return 0;
279     } else {
280       *out_len = ret;
281     }
282     ctx->poisoned = 0;
283     return 1;
284   }
285 
286   if (in_len <= 0) {
287     *out_len = 0;
288     if (in_len == 0) {
289       ctx->poisoned = 0;
290       return 1;
291     }
292     return 0;
293   }
294 
295   if (ctx->buf_len == 0 && block_remainder(ctx, in_len) == 0) {
296     if (ctx->cipher->cipher(ctx, out, in, in_len)) {
297       *out_len = in_len;
298       ctx->poisoned = 0;
299       return 1;
300     } else {
301       *out_len = 0;
302       return 0;
303     }
304   }
305 
306   int i = ctx->buf_len;
307   assert(bl <= (int)sizeof(ctx->buf));
308   if (i != 0) {
309     if (bl - i > in_len) {
310       OPENSSL_memcpy(&ctx->buf[i], in, in_len);
311       ctx->buf_len += in_len;
312       *out_len = 0;
313       ctx->poisoned = 0;
314       return 1;
315     } else {
316       int j = bl - i;
317       OPENSSL_memcpy(&ctx->buf[i], in, j);
318       if (!ctx->cipher->cipher(ctx, out, ctx->buf, bl)) {
319         return 0;
320       }
321       in_len -= j;
322       in += j;
323       out += bl;
324       *out_len = bl;
325     }
326   } else {
327     *out_len = 0;
328   }
329 
330   i = block_remainder(ctx, in_len);
331   in_len -= i;
332   if (in_len > 0) {
333     if (!ctx->cipher->cipher(ctx, out, in, in_len)) {
334       return 0;
335     }
336     *out_len += in_len;
337   }
338 
339   if (i != 0) {
340     OPENSSL_memcpy(ctx->buf, &in[in_len], i);
341   }
342   ctx->buf_len = i;
343   ctx->poisoned = 0;
344   return 1;
345 }
346 
EVP_EncryptFinal_ex(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len)347 int EVP_EncryptFinal_ex(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len) {
348   int n;
349   unsigned int i, b, bl;
350 
351   if (ctx->poisoned) {
352     OPENSSL_PUT_ERROR(CIPHER, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED);
353     return 0;
354   }
355 
356   if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
357     // When EVP_CIPH_FLAG_CUSTOM_CIPHER is set, the return value of |cipher| is
358     // the number of bytes written, or -1 on error. Otherwise the return value
359     // is one on success and zero on error.
360     const int num_bytes = ctx->cipher->cipher(ctx, out, NULL, 0);
361     if (num_bytes < 0) {
362       return 0;
363     }
364     *out_len = num_bytes;
365     goto out;
366   }
367 
368   b = ctx->cipher->block_size;
369   assert(b <= sizeof(ctx->buf));
370   if (b == 1) {
371     *out_len = 0;
372     goto out;
373   }
374 
375   bl = ctx->buf_len;
376   if (ctx->flags & EVP_CIPH_NO_PADDING) {
377     if (bl) {
378       OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH);
379       return 0;
380     }
381     *out_len = 0;
382     goto out;
383   }
384 
385   n = b - bl;
386   for (i = bl; i < b; i++) {
387     ctx->buf[i] = n;
388   }
389   if (!ctx->cipher->cipher(ctx, out, ctx->buf, b)) {
390     return 0;
391   }
392   *out_len = b;
393 
394 out:
395   EVP_Cipher_verify_service_indicator(ctx);
396   return 1;
397 }
398 
EVP_DecryptUpdate(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len,const uint8_t * in,int in_len)399 int EVP_DecryptUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len,
400                       const uint8_t *in, int in_len) {
401   if (ctx->poisoned) {
402     OPENSSL_PUT_ERROR(CIPHER, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED);
403     return 0;
404   }
405 
406   // Ciphers that use blocks may write up to |bl| extra bytes. Ensure the output
407   // does not overflow |*out_len|.
408   unsigned int b = ctx->cipher->block_size;
409   if (b > 1 && in_len > INT_MAX - (int)b) {
410     OPENSSL_PUT_ERROR(CIPHER, ERR_R_OVERFLOW);
411     return 0;
412   }
413 
414   if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
415     int r = ctx->cipher->cipher(ctx, out, in, in_len);
416     if (r < 0) {
417       *out_len = 0;
418       return 0;
419     } else {
420       *out_len = r;
421     }
422     return 1;
423   }
424 
425   if (in_len <= 0) {
426     *out_len = 0;
427     return in_len == 0;
428   }
429 
430   if (ctx->flags & EVP_CIPH_NO_PADDING) {
431     return EVP_EncryptUpdate(ctx, out, out_len, in, in_len);
432   }
433 
434   assert(b <= sizeof(ctx->final));
435   int fix_len = 0;
436   if (ctx->final_used) {
437     OPENSSL_memcpy(out, ctx->final, b);
438     out += b;
439     fix_len = 1;
440   }
441 
442   if (!EVP_EncryptUpdate(ctx, out, out_len, in, in_len)) {
443     return 0;
444   }
445 
446   // if we have 'decrypted' a multiple of block size, make sure
447   // we have a copy of this last block
448   if (b > 1 && !ctx->buf_len) {
449     *out_len -= b;
450     ctx->final_used = 1;
451     OPENSSL_memcpy(ctx->final, &out[*out_len], b);
452   } else {
453     ctx->final_used = 0;
454   }
455 
456   if (fix_len) {
457     *out_len += b;
458   }
459 
460   return 1;
461 }
462 
EVP_DecryptFinal_ex(EVP_CIPHER_CTX * ctx,unsigned char * out,int * out_len)463 int EVP_DecryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out, int *out_len) {
464   int i, n;
465   unsigned int b;
466   *out_len = 0;
467 
468   if (ctx->poisoned) {
469     OPENSSL_PUT_ERROR(CIPHER, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED);
470     return 0;
471   }
472 
473   if (ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) {
474     i = ctx->cipher->cipher(ctx, out, NULL, 0);
475     if (i < 0) {
476       return 0;
477     } else {
478       *out_len = i;
479     }
480     goto out;
481   }
482 
483   b = ctx->cipher->block_size;
484   if (ctx->flags & EVP_CIPH_NO_PADDING) {
485     if (ctx->buf_len) {
486       OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH);
487       return 0;
488     }
489     *out_len = 0;
490     goto out;
491   }
492 
493   if (b > 1) {
494     if (ctx->buf_len || !ctx->final_used) {
495       OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_WRONG_FINAL_BLOCK_LENGTH);
496       return 0;
497     }
498     assert(b <= sizeof(ctx->final));
499 
500     // The following assumes that the ciphertext has been authenticated.
501     // Otherwise it provides a padding oracle.
502     n = ctx->final[b - 1];
503     if (n == 0 || n > (int)b) {
504       OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_BAD_DECRYPT);
505       return 0;
506     }
507 
508     for (i = 0; i < n; i++) {
509       if (ctx->final[--b] != n) {
510         OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_BAD_DECRYPT);
511         return 0;
512       }
513     }
514 
515     n = ctx->cipher->block_size - n;
516     for (i = 0; i < n; i++) {
517       out[i] = ctx->final[i];
518     }
519     *out_len = n;
520   } else {
521     *out_len = 0;
522   }
523 
524 out:
525   EVP_Cipher_verify_service_indicator(ctx);
526   return 1;
527 }
528 
EVP_Cipher(EVP_CIPHER_CTX * ctx,uint8_t * out,const uint8_t * in,size_t in_len)529 int EVP_Cipher(EVP_CIPHER_CTX *ctx, uint8_t *out, const uint8_t *in,
530                size_t in_len) {
531   const int ret = ctx->cipher->cipher(ctx, out, in, in_len);
532 
533   // |EVP_CIPH_FLAG_CUSTOM_CIPHER| never sets the FIPS indicator via
534   // |EVP_Cipher| because it's complicated whether the operation has completed
535   // or not. E.g. AES-GCM with a non-NULL |in| argument hasn't completed an
536   // operation. Callers should use the |EVP_AEAD| API or, at least,
537   // |EVP_CipherUpdate| etc.
538   //
539   // This call can't be pushed into |EVP_Cipher_verify_service_indicator|
540   // because whether |ret| indicates success or not depends on whether
541   // |EVP_CIPH_FLAG_CUSTOM_CIPHER| is set. (This unreasonable, but matches
542   // OpenSSL.)
543   if (!(ctx->cipher->flags & EVP_CIPH_FLAG_CUSTOM_CIPHER) && ret) {
544     EVP_Cipher_verify_service_indicator(ctx);
545   }
546 
547   return ret;
548 }
549 
EVP_CipherUpdate(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len,const uint8_t * in,int in_len)550 int EVP_CipherUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len,
551                      const uint8_t *in, int in_len) {
552   if (ctx->encrypt) {
553     return EVP_EncryptUpdate(ctx, out, out_len, in, in_len);
554   } else {
555     return EVP_DecryptUpdate(ctx, out, out_len, in, in_len);
556   }
557 }
558 
EVP_CipherFinal_ex(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len)559 int EVP_CipherFinal_ex(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len) {
560   if (ctx->encrypt) {
561     return EVP_EncryptFinal_ex(ctx, out, out_len);
562   } else {
563     return EVP_DecryptFinal_ex(ctx, out, out_len);
564   }
565 }
566 
EVP_CIPHER_CTX_cipher(const EVP_CIPHER_CTX * ctx)567 const EVP_CIPHER *EVP_CIPHER_CTX_cipher(const EVP_CIPHER_CTX *ctx) {
568   return ctx->cipher;
569 }
570 
EVP_CIPHER_CTX_nid(const EVP_CIPHER_CTX * ctx)571 int EVP_CIPHER_CTX_nid(const EVP_CIPHER_CTX *ctx) {
572   return ctx->cipher->nid;
573 }
574 
EVP_CIPHER_CTX_encrypting(const EVP_CIPHER_CTX * ctx)575 int EVP_CIPHER_CTX_encrypting(const EVP_CIPHER_CTX *ctx) {
576   return ctx->encrypt;
577 }
578 
EVP_CIPHER_CTX_block_size(const EVP_CIPHER_CTX * ctx)579 unsigned EVP_CIPHER_CTX_block_size(const EVP_CIPHER_CTX *ctx) {
580   return ctx->cipher->block_size;
581 }
582 
EVP_CIPHER_CTX_key_length(const EVP_CIPHER_CTX * ctx)583 unsigned EVP_CIPHER_CTX_key_length(const EVP_CIPHER_CTX *ctx) {
584   return ctx->key_len;
585 }
586 
EVP_CIPHER_CTX_iv_length(const EVP_CIPHER_CTX * ctx)587 unsigned EVP_CIPHER_CTX_iv_length(const EVP_CIPHER_CTX *ctx) {
588   if (EVP_CIPHER_mode(ctx->cipher) == EVP_CIPH_GCM_MODE) {
589     int length;
590     int res = EVP_CIPHER_CTX_ctrl((EVP_CIPHER_CTX *)ctx, EVP_CTRL_GET_IVLEN, 0,
591                                   &length);
592     // EVP_CIPHER_CTX_ctrl returning an error should be impossible under this
593     // circumstance. If it somehow did, fallback to the static cipher iv_len.
594     if (res == 1) {
595       return length;
596     }
597   }
598   return ctx->cipher->iv_len;
599 }
600 
EVP_CIPHER_CTX_get_app_data(const EVP_CIPHER_CTX * ctx)601 void *EVP_CIPHER_CTX_get_app_data(const EVP_CIPHER_CTX *ctx) {
602   return ctx->app_data;
603 }
604 
EVP_CIPHER_CTX_set_app_data(EVP_CIPHER_CTX * ctx,void * data)605 void EVP_CIPHER_CTX_set_app_data(EVP_CIPHER_CTX *ctx, void *data) {
606   ctx->app_data = data;
607 }
608 
EVP_CIPHER_CTX_flags(const EVP_CIPHER_CTX * ctx)609 uint32_t EVP_CIPHER_CTX_flags(const EVP_CIPHER_CTX *ctx) {
610   return ctx->cipher->flags & ~EVP_CIPH_MODE_MASK;
611 }
612 
EVP_CIPHER_CTX_mode(const EVP_CIPHER_CTX * ctx)613 uint32_t EVP_CIPHER_CTX_mode(const EVP_CIPHER_CTX *ctx) {
614   return ctx->cipher->flags & EVP_CIPH_MODE_MASK;
615 }
616 
EVP_CIPHER_CTX_ctrl(EVP_CIPHER_CTX * ctx,int command,int arg,void * ptr)617 int EVP_CIPHER_CTX_ctrl(EVP_CIPHER_CTX *ctx, int command, int arg, void *ptr) {
618   int ret;
619   if (!ctx->cipher) {
620     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_NO_CIPHER_SET);
621     return 0;
622   }
623 
624   if (!ctx->cipher->ctrl) {
625     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_CTRL_NOT_IMPLEMENTED);
626     return 0;
627   }
628 
629   ret = ctx->cipher->ctrl(ctx, command, arg, ptr);
630   if (ret == -1) {
631     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_CTRL_OPERATION_NOT_IMPLEMENTED);
632     return 0;
633   }
634 
635   return ret;
636 }
637 
EVP_CIPHER_CTX_set_padding(EVP_CIPHER_CTX * ctx,int pad)638 int EVP_CIPHER_CTX_set_padding(EVP_CIPHER_CTX *ctx, int pad) {
639   if (pad) {
640     ctx->flags &= ~EVP_CIPH_NO_PADDING;
641   } else {
642     ctx->flags |= EVP_CIPH_NO_PADDING;
643   }
644   return 1;
645 }
646 
EVP_CIPHER_CTX_set_key_length(EVP_CIPHER_CTX * c,unsigned key_len)647 int EVP_CIPHER_CTX_set_key_length(EVP_CIPHER_CTX *c, unsigned key_len) {
648   if (c->key_len == key_len) {
649     return 1;
650   }
651 
652   if (key_len == 0 || !(c->cipher->flags & EVP_CIPH_VARIABLE_LENGTH)) {
653     OPENSSL_PUT_ERROR(CIPHER, CIPHER_R_INVALID_KEY_LENGTH);
654     return 0;
655   }
656 
657   c->key_len = key_len;
658   return 1;
659 }
660 
EVP_CIPHER_nid(const EVP_CIPHER * cipher)661 int EVP_CIPHER_nid(const EVP_CIPHER *cipher) { return cipher->nid; }
662 
EVP_CIPHER_block_size(const EVP_CIPHER * cipher)663 unsigned EVP_CIPHER_block_size(const EVP_CIPHER *cipher) {
664   return cipher->block_size;
665 }
666 
EVP_CIPHER_key_length(const EVP_CIPHER * cipher)667 unsigned EVP_CIPHER_key_length(const EVP_CIPHER *cipher) {
668   return cipher->key_len;
669 }
670 
EVP_CIPHER_iv_length(const EVP_CIPHER * cipher)671 unsigned EVP_CIPHER_iv_length(const EVP_CIPHER *cipher) {
672   return cipher->iv_len;
673 }
674 
EVP_CIPHER_flags(const EVP_CIPHER * cipher)675 uint32_t EVP_CIPHER_flags(const EVP_CIPHER *cipher) {
676   return cipher->flags & ~EVP_CIPH_MODE_MASK;
677 }
678 
EVP_CIPHER_mode(const EVP_CIPHER * cipher)679 uint32_t EVP_CIPHER_mode(const EVP_CIPHER *cipher) {
680   return cipher->flags & EVP_CIPH_MODE_MASK;
681 }
682 
EVP_CipherInit(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,const uint8_t * key,const uint8_t * iv,int enc)683 int EVP_CipherInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
684                    const uint8_t *key, const uint8_t *iv, int enc) {
685   if (cipher) {
686     EVP_CIPHER_CTX_init(ctx);
687   }
688   return EVP_CipherInit_ex(ctx, cipher, NULL, key, iv, enc);
689 }
690 
EVP_EncryptInit(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,const uint8_t * key,const uint8_t * iv)691 int EVP_EncryptInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
692                     const uint8_t *key, const uint8_t *iv) {
693   return EVP_CipherInit(ctx, cipher, key, iv, 1);
694 }
695 
EVP_DecryptInit(EVP_CIPHER_CTX * ctx,const EVP_CIPHER * cipher,const uint8_t * key,const uint8_t * iv)696 int EVP_DecryptInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
697                     const uint8_t *key, const uint8_t *iv) {
698   return EVP_CipherInit(ctx, cipher, key, iv, 0);
699 }
700 
EVP_CipherFinal(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len)701 int EVP_CipherFinal(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len) {
702   return EVP_CipherFinal_ex(ctx, out, out_len);
703 }
704 
EVP_EncryptFinal(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len)705 int EVP_EncryptFinal(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len) {
706   return EVP_EncryptFinal_ex(ctx, out, out_len);
707 }
708 
EVP_DecryptFinal(EVP_CIPHER_CTX * ctx,uint8_t * out,int * out_len)709 int EVP_DecryptFinal(EVP_CIPHER_CTX *ctx, uint8_t *out, int *out_len) {
710   return EVP_DecryptFinal_ex(ctx, out, out_len);
711 }
712 
EVP_add_cipher_alias(const char * a,const char * b)713 int EVP_add_cipher_alias(const char *a, const char *b) {
714   return 1;
715 }
716 
EVP_CIPHER_CTX_set_flags(const EVP_CIPHER_CTX * ctx,uint32_t flags)717 void EVP_CIPHER_CTX_set_flags(const EVP_CIPHER_CTX *ctx, uint32_t flags) {}
718