FIPS140 mode is detected on run-time.
[gnutls:gnutls.git] / lib / crypto-api.c
1 /*
2  * Copyright (C) 2000-2012 Free Software Foundation, Inc.
3  *
4  * Author: Nikos Mavrogiannopoulos
5  *
6  * This file is part of GnuTLS.
7  *
8  * The GnuTLS is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public License
10  * as published by the Free Software Foundation; either version 2.1 of
11  * the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful, but
14  * WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public License
19  * along with this program.  If not, see <http://www.gnu.org/licenses/>
20  *
21  */
22
23 #include <gnutls_int.h>
24 #include <gnutls_errors.h>
25 #include <gnutls_cipher_int.h>
26 #include <gnutls_datum.h>
27 #include <gnutls/crypto.h>
28 #include <algorithms.h>
29 #include <random.h>
30 #include <crypto.h>
31 #include <fips.h>
32
33 typedef struct api_cipher_hd_st {
34         cipher_hd_st ctx_enc;
35         cipher_hd_st ctx_dec;
36 } api_cipher_hd_st;
37
38 /**
39  * gnutls_cipher_init:
40  * @handle: is a #gnutls_cipher_hd_t structure.
41  * @cipher: the encryption algorithm to use
42  * @key: The key to be used for encryption
43  * @iv: The IV to use (if not applicable set NULL)
44  *
45  * This function will initialize an context that can be used for
46  * encryption/decryption of data. This will effectively use the
47  * current crypto backend in use by gnutls or the cryptographic
48  * accelerator in use.
49  *
50  * Returns: Zero or a negative error code on error.
51  *
52  * Since: 2.10.0
53  **/
54 int
55 gnutls_cipher_init(gnutls_cipher_hd_t * handle,
56                    gnutls_cipher_algorithm_t cipher,
57                    const gnutls_datum_t * key, const gnutls_datum_t * iv)
58 {
59         api_cipher_hd_st *h;
60         int ret;
61
62         *handle = gnutls_calloc(1, sizeof(api_cipher_hd_st));
63         if (*handle == NULL) {
64                 gnutls_assert();
65                 return GNUTLS_E_MEMORY_ERROR;
66         }
67
68         h = *handle;
69         ret =
70             _gnutls_cipher_init(&h->ctx_enc, cipher_to_entry(cipher), key,
71                                 iv, 1);
72
73         if (ret >= 0 && _gnutls_cipher_is_aead(&h->ctx_enc) == 0)       /* AEAD ciphers are stream - so far */
74                 ret =
75                     _gnutls_cipher_init(&h->ctx_dec,
76                                         cipher_to_entry(cipher), key, iv,
77                                         0);
78
79         return ret;
80 }
81
82 /**
83  * gnutls_cipher_tag:
84  * @handle: is a #gnutls_cipher_hd_t structure.
85  * @tag: will hold the tag
86  * @tag_size: The length of the tag to return
87  *
88  * This function operates on authenticated encryption with
89  * associated data (AEAD) ciphers and will return the
90  * output tag.
91  *
92  * Returns: Zero or a negative error code on error.
93  *
94  * Since: 3.0
95  **/
96 int
97 gnutls_cipher_tag(gnutls_cipher_hd_t handle, void *tag, size_t tag_size)
98 {
99         api_cipher_hd_st *h = handle;
100
101         if (_gnutls_cipher_is_aead(&h->ctx_enc) == 0)
102                 return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
103
104         _gnutls_cipher_tag(&h->ctx_enc, tag, tag_size);
105
106         return 0;
107 }
108
109 /**
110  * gnutls_cipher_add_auth:
111  * @handle: is a #gnutls_cipher_hd_t structure.
112  * @text: the data to be authenticated
113  * @text_size: The length of the data
114  *
115  * This function operates on authenticated encryption with
116  * associated data (AEAD) ciphers and authenticate the
117  * input data. This function can only be called once
118  * and before any encryption operations.
119  *
120  * Returns: Zero or a negative error code on error.
121  *
122  * Since: 3.0
123  **/
124 int
125 gnutls_cipher_add_auth(gnutls_cipher_hd_t handle, const void *text,
126                        size_t text_size)
127 {
128         api_cipher_hd_st *h = handle;
129
130         if (_gnutls_cipher_is_aead(&h->ctx_enc) == 0)
131                 return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
132
133         _gnutls_cipher_auth(&h->ctx_enc, text, text_size);
134
135         return 0;
136 }
137
138 /**
139  * gnutls_cipher_set_iv:
140  * @handle: is a #gnutls_cipher_hd_t structure.
141  * @iv: the IV to set
142  * @ivlen: The length of the IV
143  *
144  * This function will set the IV to be used for the next
145  * encryption block.
146  *
147  * Since: 3.0
148  **/
149 void
150 gnutls_cipher_set_iv(gnutls_cipher_hd_t handle, void *iv, size_t ivlen)
151 {
152         api_cipher_hd_st *h = handle;
153
154         _gnutls_cipher_setiv(&h->ctx_enc, iv, ivlen);
155
156         if (_gnutls_cipher_is_aead(&h->ctx_enc) == 0)
157                 _gnutls_cipher_setiv(&h->ctx_dec, iv, ivlen);
158 }
159
160 /**
161  * gnutls_cipher_encrypt:
162  * @handle: is a #gnutls_cipher_hd_t structure.
163  * @text: the data to encrypt
164  * @textlen: The length of data to encrypt
165  *
166  * This function will encrypt the given data using the algorithm
167  * specified by the context.
168  *
169  * Returns: Zero or a negative error code on error.
170  *
171  * Since: 2.10.0
172  **/
173 int
174 gnutls_cipher_encrypt(gnutls_cipher_hd_t handle, void *text,
175                       size_t textlen)
176 {
177         api_cipher_hd_st *h = handle;
178
179         return _gnutls_cipher_encrypt(&h->ctx_enc, text, textlen);
180 }
181
182 /**
183  * gnutls_cipher_decrypt:
184  * @handle: is a #gnutls_cipher_hd_t structure.
185  * @ciphertext: the data to encrypt
186  * @ciphertextlen: The length of data to encrypt
187  *
188  * This function will decrypt the given data using the algorithm
189  * specified by the context.
190  *
191  * Note that in AEAD ciphers, this will not check the tag. You will
192  * need to compare the tag sent with the value returned from gnutls_cipher_tag().
193  *
194  * Returns: Zero or a negative error code on error.
195  *
196  * Since: 2.10.0
197  **/
198 int
199 gnutls_cipher_decrypt(gnutls_cipher_hd_t handle, void *ciphertext,
200                       size_t ciphertextlen)
201 {
202         api_cipher_hd_st *h = handle;
203
204         if (_gnutls_cipher_is_aead(&h->ctx_enc) != 0)
205                 return _gnutls_cipher_decrypt(&h->ctx_enc, ciphertext,
206                                               ciphertextlen);
207         else
208                 return _gnutls_cipher_decrypt(&h->ctx_dec, ciphertext,
209                                               ciphertextlen);
210 }
211
212 /**
213  * gnutls_cipher_encrypt2:
214  * @handle: is a #gnutls_cipher_hd_t structure.
215  * @text: the data to encrypt
216  * @textlen: The length of data to encrypt
217  * @ciphertext: the encrypted data
218  * @ciphertextlen: The available length for encrypted data
219  *
220  * This function will encrypt the given data using the algorithm
221  * specified by the context.
222  *
223  * Returns: Zero or a negative error code on error.
224  *
225  * Since: 2.12.0
226  **/
227 int
228 gnutls_cipher_encrypt2(gnutls_cipher_hd_t handle, const void *text,
229                        size_t textlen, void *ciphertext,
230                        size_t ciphertextlen)
231 {
232         api_cipher_hd_st *h = handle;
233
234         return _gnutls_cipher_encrypt2(&h->ctx_enc, text, textlen,
235                                        ciphertext, ciphertextlen);
236 }
237
238 /**
239  * gnutls_cipher_decrypt2:
240  * @handle: is a #gnutls_cipher_hd_t structure.
241  * @ciphertext: the data to encrypt
242  * @ciphertextlen: The length of data to encrypt
243  * @text: the decrypted data
244  * @textlen: The available length for decrypted data
245  *
246  * This function will decrypt the given data using the algorithm
247  * specified by the context.
248  *
249  * Note that in AEAD ciphers, this will not check the tag. You will
250  * need to compare the tag sent with the value returned from gnutls_cipher_tag().
251  *
252  * Returns: Zero or a negative error code on error.
253  *
254  * Since: 2.12.0
255  **/
256 int
257 gnutls_cipher_decrypt2(gnutls_cipher_hd_t handle, const void *ciphertext,
258                        size_t ciphertextlen, void *text, size_t textlen)
259 {
260         api_cipher_hd_st *h = handle;
261
262         if (_gnutls_cipher_is_aead(&h->ctx_enc) != 0)
263                 return _gnutls_cipher_decrypt2(&h->ctx_enc, ciphertext,
264                                                ciphertextlen, text,
265                                                textlen);
266         else
267                 return _gnutls_cipher_decrypt2(&h->ctx_dec, ciphertext,
268                                                ciphertextlen, text,
269                                                textlen);
270 }
271
272 /**
273  * gnutls_cipher_deinit:
274  * @handle: is a #gnutls_cipher_hd_t structure.
275  *
276  * This function will deinitialize all resources occupied by the given
277  * encryption context.
278  *
279  * Since: 2.10.0
280  **/
281 void gnutls_cipher_deinit(gnutls_cipher_hd_t handle)
282 {
283         api_cipher_hd_st *h = handle;
284
285         _gnutls_cipher_deinit(&h->ctx_enc);
286         if (_gnutls_cipher_is_aead(&h->ctx_enc) == 0)
287                 _gnutls_cipher_deinit(&h->ctx_dec);
288         gnutls_free(handle);
289 }
290
291
292 /* HMAC */
293
294 /**
295  * gnutls_hmac_init:
296  * @dig: is a #gnutls_hmac_hd_t structure.
297  * @algorithm: the HMAC algorithm to use
298  * @key: The key to be used for encryption
299  * @keylen: The length of the key
300  *
301  * This function will initialize an context that can be used to
302  * produce a Message Authentication Code (MAC) of data.  This will
303  * effectively use the current crypto backend in use by gnutls or the
304  * cryptographic accelerator in use.
305  *
306  * Note that despite the name of this function, it can be used
307  * for other MAC algorithms than HMAC.
308  *
309  * Returns: Zero or a negative error code on error.
310  *
311  * Since: 2.10.0
312  **/
313 int
314 gnutls_hmac_init(gnutls_hmac_hd_t * dig,
315                  gnutls_mac_algorithm_t algorithm,
316                  const void *key, size_t keylen)
317 {
318 #ifdef ENABLE_FIPS140
319         /* MD5 is only allowed internally for TLS */
320         if (_gnutls_fips_mode_enabled() != 0 &&
321                 _gnutls_get_lib_state() != LIB_STATE_SELFTEST) {
322
323                 if (algorithm == GNUTLS_MAC_MD5)
324                         return gnutls_assert_val(GNUTLS_E_UNWANTED_ALGORITHM);
325         }
326 #endif
327
328         *dig = gnutls_malloc(sizeof(mac_hd_st));
329         if (*dig == NULL) {
330                 gnutls_assert();
331                 return GNUTLS_E_MEMORY_ERROR;
332         }
333
334         return _gnutls_mac_init(((mac_hd_st *) * dig),
335                                 mac_to_entry(algorithm), key, keylen);
336 }
337
338 /**
339  * gnutls_hmac_set_nonce:
340  * @handle: is a #gnutls_cipher_hd_t structure.
341  * @nonce: the data to set as nonce
342  * @nonce_len: The length of data
343  *
344  * This function will set the nonce in the MAC algorithm.
345  *
346  * Since: 3.2.0
347  **/
348 void
349 gnutls_hmac_set_nonce(gnutls_hmac_hd_t handle, const void *nonce,
350                       size_t nonce_len)
351 {
352         _gnutls_mac_set_nonce((mac_hd_st *) handle, nonce, nonce_len);
353 }
354
355 /**
356  * gnutls_hmac:
357  * @handle: is a #gnutls_cipher_hd_t structure.
358  * @text: the data to hash
359  * @textlen: The length of data to hash
360  *
361  * This function will hash the given data using the algorithm
362  * specified by the context.
363  *
364  * Returns: Zero or a negative error code on error.
365  *
366  * Since: 2.10.0
367  **/
368 int gnutls_hmac(gnutls_hmac_hd_t handle, const void *text, size_t textlen)
369 {
370         return _gnutls_mac((mac_hd_st *) handle, text, textlen);
371 }
372
373 /**
374  * gnutls_hmac_output:
375  * @handle: is a #gnutls_hmac_hd_t structure.
376  * @digest: is the output value of the MAC
377  *
378  * This function will output the current MAC value
379  * and reset the state of the MAC.
380  *
381  * Since: 2.10.0
382  **/
383 void gnutls_hmac_output(gnutls_hmac_hd_t handle, void *digest)
384 {
385         _gnutls_mac_output((mac_hd_st *) handle, digest);
386 }
387
388 /**
389  * gnutls_hmac_deinit:
390  * @handle: is a #gnutls_hmac_hd_t structure.
391  * @digest: is the output value of the MAC
392  *
393  * This function will deinitialize all resources occupied by
394  * the given hmac context.
395  *
396  * Since: 2.10.0
397  **/
398 void gnutls_hmac_deinit(gnutls_hmac_hd_t handle, void *digest)
399 {
400         _gnutls_mac_deinit((mac_hd_st *) handle, digest);
401         gnutls_free(handle);
402 }
403
404 /**
405  * gnutls_hmac_get_len:
406  * @algorithm: the hmac algorithm to use
407  *
408  * This function will return the length of the output data
409  * of the given hmac algorithm.
410  *
411  * Returns: The length or zero on error.
412  *
413  * Since: 2.10.0
414  **/
415 int gnutls_hmac_get_len(gnutls_mac_algorithm_t algorithm)
416 {
417         return _gnutls_mac_get_algo_len(mac_to_entry(algorithm));
418 }
419
420 /**
421  * gnutls_hmac_fast:
422  * @algorithm: the hash algorithm to use
423  * @key: the key to use
424  * @keylen: The length of the key
425  * @text: the data to hash
426  * @textlen: The length of data to hash
427  * @digest: is the output value of the hash
428  *
429  * This convenience function will hash the given data and return output
430  * on a single call.
431  *
432  * Returns: Zero or a negative error code on error.
433  *
434  * Since: 2.10.0
435  **/
436 int
437 gnutls_hmac_fast(gnutls_mac_algorithm_t algorithm,
438                  const void *key, size_t keylen,
439                  const void *text, size_t textlen, void *digest)
440 {
441         return _gnutls_mac_fast(algorithm, key, keylen, text, textlen,
442                                 digest);
443 }
444
445 /* HASH */
446
447 /**
448  * gnutls_hash_init:
449  * @dig: is a #gnutls_hash_hd_t structure.
450  * @algorithm: the hash algorithm to use
451  *
452  * This function will initialize an context that can be used to
453  * produce a Message Digest of data.  This will effectively use the
454  * current crypto backend in use by gnutls or the cryptographic
455  * accelerator in use.
456  *
457  * Returns: Zero or a negative error code on error.
458  *
459  * Since: 2.10.0
460  **/
461 int
462 gnutls_hash_init(gnutls_hash_hd_t * dig,
463                  gnutls_digest_algorithm_t algorithm)
464 {
465 #ifdef ENABLE_FIPS140
466         /* MD5 is only allowed internally for TLS */
467         if (_gnutls_fips_mode_enabled() != 0 &&
468                 _gnutls_get_lib_state() != LIB_STATE_SELFTEST) {
469
470                 if (algorithm == GNUTLS_DIG_MD5)
471                         return gnutls_assert_val(GNUTLS_E_UNWANTED_ALGORITHM);
472         }
473 #endif
474
475         *dig = gnutls_malloc(sizeof(digest_hd_st));
476         if (*dig == NULL) {
477                 gnutls_assert();
478                 return GNUTLS_E_MEMORY_ERROR;
479         }
480
481         return _gnutls_hash_init(((digest_hd_st *) * dig),
482                                  mac_to_entry(algorithm));
483 }
484
485 /**
486  * gnutls_hash:
487  * @handle: is a #gnutls_cipher_hd_t structure.
488  * @text: the data to hash
489  * @textlen: The length of data to hash
490  *
491  * This function will hash the given data using the algorithm
492  * specified by the context.
493  *
494  * Returns: Zero or a negative error code on error.
495  *
496  * Since: 2.10.0
497  **/
498 int gnutls_hash(gnutls_hash_hd_t handle, const void *text, size_t textlen)
499 {
500         return _gnutls_hash((digest_hd_st *) handle, text, textlen);
501 }
502
503 /**
504  * gnutls_hash_output:
505  * @handle: is a #gnutls_hash_hd_t structure.
506  * @digest: is the output value of the hash
507  *
508  * This function will output the current hash value
509  * and reset the state of the hash.
510  *
511  * Since: 2.10.0
512  **/
513 void gnutls_hash_output(gnutls_hash_hd_t handle, void *digest)
514 {
515         _gnutls_hash_output((digest_hd_st *) handle, digest);
516 }
517
518 /**
519  * gnutls_hash_deinit:
520  * @handle: is a #gnutls_hash_hd_t structure.
521  * @digest: is the output value of the hash
522  *
523  * This function will deinitialize all resources occupied by
524  * the given hash context.
525  *
526  * Since: 2.10.0
527  **/
528 void gnutls_hash_deinit(gnutls_hash_hd_t handle, void *digest)
529 {
530         _gnutls_hash_deinit((digest_hd_st *) handle, digest);
531         gnutls_free(handle);
532 }
533
534 /**
535  * gnutls_hash_get_len:
536  * @algorithm: the hash algorithm to use
537  *
538  * This function will return the length of the output data
539  * of the given hash algorithm.
540  *
541  * Returns: The length or zero on error.
542  *
543  * Since: 2.10.0
544  **/
545 int gnutls_hash_get_len(gnutls_digest_algorithm_t algorithm)
546 {
547         return _gnutls_hash_get_algo_len(mac_to_entry(algorithm));
548 }
549
550 /**
551  * gnutls_hash_fast:
552  * @algorithm: the hash algorithm to use
553  * @text: the data to hash
554  * @textlen: The length of data to hash
555  * @digest: is the output value of the hash
556  *
557  * This convenience function will hash the given data and return output
558  * on a single call.
559  *
560  * Returns: Zero or a negative error code on error.
561  *
562  * Since: 2.10.0
563  **/
564 int
565 gnutls_hash_fast(gnutls_digest_algorithm_t algorithm,
566                  const void *text, size_t textlen, void *digest)
567 {
568         return _gnutls_hash_fast(algorithm, text, textlen, digest);
569 }
570
571 /**
572  * gnutls_key_generate:
573  * @key: is a pointer to a #gnutls_datum_t which will contain a newly
574  * created key.
575  * @key_size: The number of bytes of the key.
576  *
577  * Generates a random key of @key_size bytes.
578  *
579  * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, or an
580  * error code.
581  *
582  * Since: 3.0
583  **/
584 int gnutls_key_generate(gnutls_datum_t * key, unsigned int key_size)
585 {
586         int ret;
587
588 #ifdef ENABLE_FIPS140
589         /* The FIPS140 approved RNGs are not allowed to be used
590          * to extract key sizes longer than their original seed.
591          */
592         if (_gnutls_fips_mode_enabled() != 0 &&
593             key_size > FIPS140_RND_KEY_SIZE)
594                 return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
595 #endif
596
597         key->size = key_size;
598         key->data = gnutls_malloc(key->size);
599         if (!key->data) {
600                 gnutls_assert();
601                 return GNUTLS_E_MEMORY_ERROR;
602         }
603
604         ret = _gnutls_rnd(GNUTLS_RND_RANDOM, key->data, key->size);
605         if (ret < 0) {
606                 gnutls_assert();
607                 _gnutls_free_datum(key);
608                 return ret;
609         }
610
611         return 0;
612 }