1 /*
2  * Copyright 2011-2020 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 <stdlib.h>
11 #include <string.h>
12 #include <openssl/crypto.h>
13 #include <openssl/err.h>
14 #include <openssl/rand.h>
15 #include "modes_local.h"
16 #include "internal/thread_once.h"
17 #include "rand_local.h"
18 
19 /*
20  * Implementation of NIST SP 800-90A CTR DRBG.
21  */
22 
inc_128(RAND_DRBG_CTR * ctr)23 static void inc_128(RAND_DRBG_CTR *ctr)
24 {
25     unsigned char *p = &ctr->V[0];
26     u32 n = 16, c = 1;
27 
28     do {
29         --n;
30         c += p[n];
31         p[n] = (u8)c;
32         c >>= 8;
33     } while (n);
34 }
35 
ctr_XOR(RAND_DRBG_CTR * ctr,const unsigned char * in,size_t inlen)36 static void ctr_XOR(RAND_DRBG_CTR *ctr, const unsigned char *in, size_t inlen)
37 {
38     size_t i, n;
39 
40     if (in == NULL || inlen == 0)
41         return;
42 
43     /*
44      * Any zero padding will have no effect on the result as we
45      * are XORing. So just process however much input we have.
46      */
47     n = inlen < ctr->keylen ? inlen : ctr->keylen;
48     for (i = 0; i < n; i++)
49         ctr->K[i] ^= in[i];
50     if (inlen <= ctr->keylen)
51         return;
52 
53     n = inlen - ctr->keylen;
54     if (n > 16) {
55         /* Should never happen */
56         n = 16;
57     }
58     for (i = 0; i < n; i++)
59         ctr->V[i] ^= in[i + ctr->keylen];
60 }
61 
62 /*
63  * Process a complete block using BCC algorithm of SP 800-90A 10.3.3
64  */
ctr_BCC_block(RAND_DRBG_CTR * ctr,unsigned char * out,const unsigned char * in)65 __owur static int ctr_BCC_block(RAND_DRBG_CTR *ctr, unsigned char *out,
66                                 const unsigned char *in)
67 {
68     int i, outlen = AES_BLOCK_SIZE;
69 
70     for (i = 0; i < 16; i++)
71         out[i] ^= in[i];
72 
73     if (!EVP_CipherUpdate(ctr->ctx_df, out, &outlen, out, AES_BLOCK_SIZE)
74         || outlen != AES_BLOCK_SIZE)
75         return 0;
76     return 1;
77 }
78 
79 
80 /*
81  * Handle several BCC operations for as much data as we need for K and X
82  */
ctr_BCC_blocks(RAND_DRBG_CTR * ctr,const unsigned char * in)83 __owur static int ctr_BCC_blocks(RAND_DRBG_CTR *ctr, const unsigned char *in)
84 {
85     if (!ctr_BCC_block(ctr, ctr->KX, in)
86         || !ctr_BCC_block(ctr, ctr->KX + 16, in))
87         return 0;
88     if (ctr->keylen != 16 && !ctr_BCC_block(ctr, ctr->KX + 32, in))
89         return 0;
90     return 1;
91 }
92 
93 /*
94  * Initialise BCC blocks: these have the value 0,1,2 in leftmost positions:
95  * see 10.3.1 stage 7.
96  */
ctr_BCC_init(RAND_DRBG_CTR * ctr)97 __owur static int ctr_BCC_init(RAND_DRBG_CTR *ctr)
98 {
99     memset(ctr->KX, 0, 48);
100     memset(ctr->bltmp, 0, 16);
101     if (!ctr_BCC_block(ctr, ctr->KX, ctr->bltmp))
102         return 0;
103     ctr->bltmp[3] = 1;
104     if (!ctr_BCC_block(ctr, ctr->KX + 16, ctr->bltmp))
105         return 0;
106     if (ctr->keylen != 16) {
107         ctr->bltmp[3] = 2;
108         if (!ctr_BCC_block(ctr, ctr->KX + 32, ctr->bltmp))
109             return 0;
110     }
111     return 1;
112 }
113 
114 /*
115  * Process several blocks into BCC algorithm, some possibly partial
116  */
ctr_BCC_update(RAND_DRBG_CTR * ctr,const unsigned char * in,size_t inlen)117 __owur static int ctr_BCC_update(RAND_DRBG_CTR *ctr,
118                                  const unsigned char *in, size_t inlen)
119 {
120     if (in == NULL || inlen == 0)
121         return 1;
122 
123     /* If we have partial block handle it first */
124     if (ctr->bltmp_pos) {
125         size_t left = 16 - ctr->bltmp_pos;
126 
127         /* If we now have a complete block process it */
128         if (inlen >= left) {
129             memcpy(ctr->bltmp + ctr->bltmp_pos, in, left);
130             if (!ctr_BCC_blocks(ctr, ctr->bltmp))
131                 return 0;
132             ctr->bltmp_pos = 0;
133             inlen -= left;
134             in += left;
135         }
136     }
137 
138     /* Process zero or more complete blocks */
139     for (; inlen >= 16; in += 16, inlen -= 16) {
140         if (!ctr_BCC_blocks(ctr, in))
141             return 0;
142     }
143 
144     /* Copy any remaining partial block to the temporary buffer */
145     if (inlen > 0) {
146         memcpy(ctr->bltmp + ctr->bltmp_pos, in, inlen);
147         ctr->bltmp_pos += inlen;
148     }
149     return 1;
150 }
151 
ctr_BCC_final(RAND_DRBG_CTR * ctr)152 __owur static int ctr_BCC_final(RAND_DRBG_CTR *ctr)
153 {
154     if (ctr->bltmp_pos) {
155         memset(ctr->bltmp + ctr->bltmp_pos, 0, 16 - ctr->bltmp_pos);
156         if (!ctr_BCC_blocks(ctr, ctr->bltmp))
157             return 0;
158     }
159     return 1;
160 }
161 
ctr_df(RAND_DRBG_CTR * ctr,const unsigned char * in1,size_t in1len,const unsigned char * in2,size_t in2len,const unsigned char * in3,size_t in3len)162 __owur static int ctr_df(RAND_DRBG_CTR *ctr,
163                          const unsigned char *in1, size_t in1len,
164                          const unsigned char *in2, size_t in2len,
165                          const unsigned char *in3, size_t in3len)
166 {
167     static unsigned char c80 = 0x80;
168     size_t inlen;
169     unsigned char *p = ctr->bltmp;
170     int outlen = AES_BLOCK_SIZE;
171 
172     if (!ctr_BCC_init(ctr))
173         return 0;
174     if (in1 == NULL)
175         in1len = 0;
176     if (in2 == NULL)
177         in2len = 0;
178     if (in3 == NULL)
179         in3len = 0;
180     inlen = in1len + in2len + in3len;
181     /* Initialise L||N in temporary block */
182     *p++ = (inlen >> 24) & 0xff;
183     *p++ = (inlen >> 16) & 0xff;
184     *p++ = (inlen >> 8) & 0xff;
185     *p++ = inlen & 0xff;
186 
187     /* NB keylen is at most 32 bytes */
188     *p++ = 0;
189     *p++ = 0;
190     *p++ = 0;
191     *p = (unsigned char)((ctr->keylen + 16) & 0xff);
192     ctr->bltmp_pos = 8;
193     if (!ctr_BCC_update(ctr, in1, in1len)
194         || !ctr_BCC_update(ctr, in2, in2len)
195         || !ctr_BCC_update(ctr, in3, in3len)
196         || !ctr_BCC_update(ctr, &c80, 1)
197         || !ctr_BCC_final(ctr))
198         return 0;
199     /* Set up key K */
200     if (!EVP_CipherInit_ex(ctr->ctx, ctr->cipher, NULL, ctr->KX, NULL, 1))
201         return 0;
202     /* X follows key K */
203     if (!EVP_CipherUpdate(ctr->ctx, ctr->KX, &outlen, ctr->KX + ctr->keylen,
204                           AES_BLOCK_SIZE)
205         || outlen != AES_BLOCK_SIZE)
206         return 0;
207     if (!EVP_CipherUpdate(ctr->ctx, ctr->KX + 16, &outlen, ctr->KX,
208                           AES_BLOCK_SIZE)
209         || outlen != AES_BLOCK_SIZE)
210         return 0;
211     if (ctr->keylen != 16)
212         if (!EVP_CipherUpdate(ctr->ctx, ctr->KX + 32, &outlen, ctr->KX + 16,
213                               AES_BLOCK_SIZE)
214             || outlen != AES_BLOCK_SIZE)
215             return 0;
216     return 1;
217 }
218 
219 /*
220  * NB the no-df Update in SP800-90A specifies a constant input length
221  * of seedlen, however other uses of this algorithm pad the input with
222  * zeroes if necessary and have up to two parameters XORed together,
223  * so we handle both cases in this function instead.
224  */
ctr_update(RAND_DRBG * drbg,const unsigned char * in1,size_t in1len,const unsigned char * in2,size_t in2len,const unsigned char * nonce,size_t noncelen)225 __owur static int ctr_update(RAND_DRBG *drbg,
226                              const unsigned char *in1, size_t in1len,
227                              const unsigned char *in2, size_t in2len,
228                              const unsigned char *nonce, size_t noncelen)
229 {
230     RAND_DRBG_CTR *ctr = &drbg->data.ctr;
231     int outlen = AES_BLOCK_SIZE;
232 
233     /* correct key is already set up. */
234     inc_128(ctr);
235     if (!EVP_CipherUpdate(ctr->ctx, ctr->K, &outlen, ctr->V, AES_BLOCK_SIZE)
236         || outlen != AES_BLOCK_SIZE)
237         return 0;
238 
239     /* If keylen longer than 128 bits need extra encrypt */
240     if (ctr->keylen != 16) {
241         inc_128(ctr);
242         if (!EVP_CipherUpdate(ctr->ctx, ctr->K+16, &outlen, ctr->V,
243                               AES_BLOCK_SIZE)
244             || outlen != AES_BLOCK_SIZE)
245             return 0;
246     }
247     inc_128(ctr);
248     if (!EVP_CipherUpdate(ctr->ctx, ctr->V, &outlen, ctr->V, AES_BLOCK_SIZE)
249         || outlen != AES_BLOCK_SIZE)
250         return 0;
251 
252     /* If 192 bit key part of V is on end of K */
253     if (ctr->keylen == 24) {
254         memcpy(ctr->V + 8, ctr->V, 8);
255         memcpy(ctr->V, ctr->K + 24, 8);
256     }
257 
258     if ((drbg->flags & RAND_DRBG_FLAG_CTR_NO_DF) == 0) {
259         /* If no input reuse existing derived value */
260         if (in1 != NULL || nonce != NULL || in2 != NULL)
261             if (!ctr_df(ctr, in1, in1len, nonce, noncelen, in2, in2len))
262                 return 0;
263         /* If this a reuse input in1len != 0 */
264         if (in1len)
265             ctr_XOR(ctr, ctr->KX, drbg->seedlen);
266     } else {
267         ctr_XOR(ctr, in1, in1len);
268         ctr_XOR(ctr, in2, in2len);
269     }
270 
271     if (!EVP_CipherInit_ex(ctr->ctx, ctr->cipher, NULL, ctr->K, NULL, 1))
272         return 0;
273     return 1;
274 }
275 
drbg_ctr_instantiate(RAND_DRBG * drbg,const unsigned char * entropy,size_t entropylen,const unsigned char * nonce,size_t noncelen,const unsigned char * pers,size_t perslen)276 __owur static int drbg_ctr_instantiate(RAND_DRBG *drbg,
277                                        const unsigned char *entropy, size_t entropylen,
278                                        const unsigned char *nonce, size_t noncelen,
279                                        const unsigned char *pers, size_t perslen)
280 {
281     RAND_DRBG_CTR *ctr = &drbg->data.ctr;
282 
283     if (entropy == NULL)
284         return 0;
285 
286     memset(ctr->K, 0, sizeof(ctr->K));
287     memset(ctr->V, 0, sizeof(ctr->V));
288     if (!EVP_CipherInit_ex(ctr->ctx, ctr->cipher, NULL, ctr->K, NULL, 1))
289         return 0;
290     if (!ctr_update(drbg, entropy, entropylen, pers, perslen, nonce, noncelen))
291         return 0;
292     return 1;
293 }
294 
drbg_ctr_reseed(RAND_DRBG * drbg,const unsigned char * entropy,size_t entropylen,const unsigned char * adin,size_t adinlen)295 __owur static int drbg_ctr_reseed(RAND_DRBG *drbg,
296                                   const unsigned char *entropy, size_t entropylen,
297                                   const unsigned char *adin, size_t adinlen)
298 {
299     if (entropy == NULL)
300         return 0;
301     if (!ctr_update(drbg, entropy, entropylen, adin, adinlen, NULL, 0))
302         return 0;
303     return 1;
304 }
305 
drbg_ctr_generate(RAND_DRBG * drbg,unsigned char * out,size_t outlen,const unsigned char * adin,size_t adinlen)306 __owur static int drbg_ctr_generate(RAND_DRBG *drbg,
307                                     unsigned char *out, size_t outlen,
308                                     const unsigned char *adin, size_t adinlen)
309 {
310     RAND_DRBG_CTR *ctr = &drbg->data.ctr;
311 
312     if (adin != NULL && adinlen != 0) {
313         if (!ctr_update(drbg, adin, adinlen, NULL, 0, NULL, 0))
314             return 0;
315         /* This means we reuse derived value */
316         if ((drbg->flags & RAND_DRBG_FLAG_CTR_NO_DF) == 0) {
317             adin = NULL;
318             adinlen = 1;
319         }
320     } else {
321         adinlen = 0;
322     }
323 
324     for ( ; ; ) {
325         int outl = AES_BLOCK_SIZE;
326 
327         inc_128(ctr);
328         if (outlen < 16) {
329             /* Use K as temp space as it will be updated */
330             if (!EVP_CipherUpdate(ctr->ctx, ctr->K, &outl, ctr->V,
331                                   AES_BLOCK_SIZE)
332                 || outl != AES_BLOCK_SIZE)
333                 return 0;
334             memcpy(out, ctr->K, outlen);
335             break;
336         }
337         if (!EVP_CipherUpdate(ctr->ctx, out, &outl, ctr->V, AES_BLOCK_SIZE)
338             || outl != AES_BLOCK_SIZE)
339             return 0;
340         out += 16;
341         outlen -= 16;
342         if (outlen == 0)
343             break;
344     }
345 
346     if (!ctr_update(drbg, adin, adinlen, NULL, 0, NULL, 0))
347         return 0;
348     return 1;
349 }
350 
drbg_ctr_uninstantiate(RAND_DRBG * drbg)351 static int drbg_ctr_uninstantiate(RAND_DRBG *drbg)
352 {
353     EVP_CIPHER_CTX_free(drbg->data.ctr.ctx);
354     EVP_CIPHER_CTX_free(drbg->data.ctr.ctx_df);
355     OPENSSL_cleanse(&drbg->data.ctr, sizeof(drbg->data.ctr));
356     return 1;
357 }
358 
359 static RAND_DRBG_METHOD drbg_ctr_meth = {
360     drbg_ctr_instantiate,
361     drbg_ctr_reseed,
362     drbg_ctr_generate,
363     drbg_ctr_uninstantiate
364 };
365 
drbg_ctr_init(RAND_DRBG * drbg)366 int drbg_ctr_init(RAND_DRBG *drbg)
367 {
368     RAND_DRBG_CTR *ctr = &drbg->data.ctr;
369     size_t keylen;
370 
371     switch (drbg->type) {
372     default:
373         /* This can't happen, but silence the compiler warning. */
374         return 0;
375     case NID_aes_128_ctr:
376         keylen = 16;
377         ctr->cipher = EVP_aes_128_ecb();
378         break;
379     case NID_aes_192_ctr:
380         keylen = 24;
381         ctr->cipher = EVP_aes_192_ecb();
382         break;
383     case NID_aes_256_ctr:
384         keylen = 32;
385         ctr->cipher = EVP_aes_256_ecb();
386         break;
387     }
388 
389     drbg->meth = &drbg_ctr_meth;
390 
391     ctr->keylen = keylen;
392     if (ctr->ctx == NULL)
393         ctr->ctx = EVP_CIPHER_CTX_new();
394     if (ctr->ctx == NULL)
395         return 0;
396     drbg->strength = keylen * 8;
397     drbg->seedlen = keylen + 16;
398 
399     if ((drbg->flags & RAND_DRBG_FLAG_CTR_NO_DF) == 0) {
400         /* df initialisation */
401         static const unsigned char df_key[32] = {
402             0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
403             0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
404             0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
405             0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f
406         };
407 
408         if (ctr->ctx_df == NULL)
409             ctr->ctx_df = EVP_CIPHER_CTX_new();
410         if (ctr->ctx_df == NULL)
411             return 0;
412         /* Set key schedule for df_key */
413         if (!EVP_CipherInit_ex(ctr->ctx_df, ctr->cipher, NULL, df_key, NULL, 1))
414             return 0;
415 
416         drbg->min_entropylen = ctr->keylen;
417         drbg->max_entropylen = DRBG_MAX_LENGTH;
418         drbg->min_noncelen = drbg->min_entropylen / 2;
419         drbg->max_noncelen = DRBG_MAX_LENGTH;
420         drbg->max_perslen = DRBG_MAX_LENGTH;
421         drbg->max_adinlen = DRBG_MAX_LENGTH;
422     } else {
423         drbg->min_entropylen = drbg->seedlen;
424         drbg->max_entropylen = drbg->seedlen;
425         /* Nonce not used */
426         drbg->min_noncelen = 0;
427         drbg->max_noncelen = 0;
428         drbg->max_perslen = drbg->seedlen;
429         drbg->max_adinlen = drbg->seedlen;
430     }
431 
432     drbg->max_request = 1 << 16;
433 
434     return 1;
435 }
436