1 /* gc-gnulib.c --- Common gnulib internal crypto interface functions
2 * Copyright (C) 2002-2011 Free Software Foundation, Inc.
4 * This file is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published
6 * by the Free Software Foundation; either version 2, or (at your
7 * option) any later version.
9 * This file is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this file; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21 /* Note: This file is only built if GC uses internal functions. */
32 #ifdef GNULIB_GC_RANDOM
34 # include <sys/types.h>
35 # include <sys/stat.h>
53 #if defined(GNULIB_GC_HMAC_MD5) || defined(GNULIB_GC_HMAC_SHA1)
58 #ifdef GNULIB_GC_ARCFOUR
61 #ifdef GNULIB_GC_ARCTWO
67 #ifdef GNULIB_GC_RIJNDAEL
68 # include "rijndael-api-fst.h"
71 /* The results of open() in this file are not used with fchdir,
72 therefore save some unnecessary work in fchdir.c. */
76 #ifdef GNULIB_GC_RANDOM
77 # if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
79 # include <wincrypt.h>
80 HCRYPTPROV g_hProv = 0;
81 # ifndef PROV_INTEL_SEC
82 # define PROV_INTEL_SEC 22
84 # ifndef CRYPT_VERIFY_CONTEXT
85 # define CRYPT_VERIFY_CONTEXT 0xF0000000
93 #ifdef GNULIB_GC_RANDOM
94 # if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
96 CryptReleaseContext (g_hProv, 0);
98 /* There is no need to create a container for just random data, so
99 we can use CRYPT_VERIFY_CONTEXT (one call) see:
100 http://blogs.msdn.com/dangriff/archive/2003/11/19/51709.aspx */
102 /* We first try to use the Intel PIII RNG if drivers are present */
103 if (!CryptAcquireContext (&g_hProv, NULL, NULL,
104 PROV_INTEL_SEC, CRYPT_VERIFY_CONTEXT))
106 /* not a PIII or no drivers available, use default RSA CSP */
107 if (!CryptAcquireContext (&g_hProv, NULL, NULL,
108 PROV_RSA_FULL, CRYPT_VERIFY_CONTEXT))
109 return GC_RANDOM_ERROR;
120 #ifdef GNULIB_GC_RANDOM
121 # if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
124 CryptReleaseContext (g_hProv, 0);
133 #ifdef GNULIB_GC_RANDOM
138 randomize (int level, char *data, size_t datalen)
140 #if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
142 return GC_RANDOM_ERROR;
143 CryptGenRandom (g_hProv, (DWORD) datalen, data);
153 device = NAME_OF_NONCE_DEVICE;
157 device = NAME_OF_PSEUDO_RANDOM_DEVICE;
161 device = NAME_OF_RANDOM_DEVICE;
165 if (strcmp (device, "no") == 0)
166 return GC_RANDOM_ERROR;
168 fd = open (device, O_RDONLY);
170 return GC_RANDOM_ERROR;
176 tmp = read (fd, data, datalen);
180 int save_errno = errno;
183 return GC_RANDOM_ERROR;
188 while (len < datalen);
192 return GC_RANDOM_ERROR;
199 gc_nonce (char *data, size_t datalen)
201 return randomize (0, data, datalen);
205 gc_pseudo_random (char *data, size_t datalen)
207 return randomize (1, data, datalen);
211 gc_random (char *data, size_t datalen)
213 return randomize (2, data, datalen);
218 /* Memory allocation. */
221 gc_set_allocators (gc_malloc_t func_malloc,
222 gc_malloc_t secure_malloc,
223 gc_secure_check_t secure_check,
224 gc_realloc_t func_realloc, gc_free_t func_free)
231 typedef struct _gc_cipher_ctx
235 #ifdef GNULIB_GC_ARCTWO
236 arctwo_context arctwoContext;
237 char arctwoIV[ARCTWO_BLOCK_SIZE];
239 #ifdef GNULIB_GC_ARCFOUR
240 arcfour_context arcfourContext;
243 gl_des_ctx desContext;
245 #ifdef GNULIB_GC_RIJNDAEL
246 rijndaelKeyInstance aesEncKey;
247 rijndaelKeyInstance aesDecKey;
248 rijndaelCipherInstance aesContext;
253 gc_cipher_open (Gc_cipher alg, Gc_cipher_mode mode,
254 gc_cipher_handle * outhandle)
259 ctx = calloc (sizeof (*ctx), 1);
261 return GC_MALLOC_ERROR;
268 #ifdef GNULIB_GC_ARCTWO
277 rc = GC_INVALID_CIPHER;
282 #ifdef GNULIB_GC_ARCFOUR
291 rc = GC_INVALID_CIPHER;
304 rc = GC_INVALID_CIPHER;
309 #ifdef GNULIB_GC_RIJNDAEL
320 rc = GC_INVALID_CIPHER;
326 rc = GC_INVALID_CIPHER;
338 gc_cipher_setkey (gc_cipher_handle handle, size_t keylen, const char *key)
340 _gc_cipher_ctx *ctx = handle;
344 #ifdef GNULIB_GC_ARCTWO
346 arctwo_setkey (&ctx->arctwoContext, keylen, key);
350 #ifdef GNULIB_GC_ARCFOUR
353 arcfour_setkey (&ctx->arcfourContext, key, keylen);
360 return GC_INVALID_CIPHER;
361 gl_des_setkey (&ctx->desContext, key);
365 #ifdef GNULIB_GC_RIJNDAEL
372 char keyMaterial[RIJNDAEL_MAX_KEY_SIZE + 1];
374 for (i = 0; i < keylen; i++)
375 sprintf (&keyMaterial[2 * i], "%02x", key[i] & 0xFF);
377 rc = rijndaelMakeKey (&ctx->aesEncKey, RIJNDAEL_DIR_ENCRYPT,
378 keylen * 8, keyMaterial);
380 return GC_INVALID_CIPHER;
382 rc = rijndaelMakeKey (&ctx->aesDecKey, RIJNDAEL_DIR_DECRYPT,
383 keylen * 8, keyMaterial);
385 return GC_INVALID_CIPHER;
387 rc = rijndaelCipherInit (&ctx->aesContext, RIJNDAEL_MODE_ECB, NULL);
389 return GC_INVALID_CIPHER;
395 return GC_INVALID_CIPHER;
402 gc_cipher_setiv (gc_cipher_handle handle, size_t ivlen, const char *iv)
404 _gc_cipher_ctx *ctx = handle;
408 #ifdef GNULIB_GC_ARCTWO
410 if (ivlen != ARCTWO_BLOCK_SIZE)
411 return GC_INVALID_CIPHER;
412 memcpy (ctx->arctwoIV, iv, ivlen);
416 #ifdef GNULIB_GC_RIJNDAEL
423 /* Doesn't use IV. */
430 char ivMaterial[2 * RIJNDAEL_MAX_IV_SIZE + 1];
432 for (i = 0; i < ivlen; i++)
433 sprintf (&ivMaterial[2 * i], "%02x", iv[i] & 0xFF);
435 rc = rijndaelCipherInit (&ctx->aesContext, RIJNDAEL_MODE_CBC,
438 return GC_INVALID_CIPHER;
443 return GC_INVALID_CIPHER;
449 return GC_INVALID_CIPHER;
456 gc_cipher_encrypt_inline (gc_cipher_handle handle, size_t len, char *data)
458 _gc_cipher_ctx *ctx = handle;
462 #ifdef GNULIB_GC_ARCTWO
467 arctwo_encrypt (&ctx->arctwoContext, data, data, len);
471 for (; len >= ARCTWO_BLOCK_SIZE; len -= ARCTWO_BLOCK_SIZE,
472 data += ARCTWO_BLOCK_SIZE)
475 for (i = 0; i < ARCTWO_BLOCK_SIZE; i++)
476 data[i] ^= ctx->arctwoIV[i];
477 arctwo_encrypt (&ctx->arctwoContext, data, data,
479 memcpy (ctx->arctwoIV, data, ARCTWO_BLOCK_SIZE);
484 return GC_INVALID_CIPHER;
489 #ifdef GNULIB_GC_ARCFOUR
492 arcfour_stream (&ctx->arcfourContext, data, data, len);
498 for (; len >= 8; len -= 8, data += 8)
499 gl_des_ecb_encrypt (&ctx->desContext, data, data);
503 #ifdef GNULIB_GC_RIJNDAEL
510 nblocks = rijndaelBlockEncrypt (&ctx->aesContext, &ctx->aesEncKey,
511 data, 8 * len, data);
513 return GC_INVALID_CIPHER;
519 return GC_INVALID_CIPHER;
526 gc_cipher_decrypt_inline (gc_cipher_handle handle, size_t len, char *data)
528 _gc_cipher_ctx *ctx = handle;
532 #ifdef GNULIB_GC_ARCTWO
537 arctwo_decrypt (&ctx->arctwoContext, data, data, len);
541 for (; len >= ARCTWO_BLOCK_SIZE; len -= ARCTWO_BLOCK_SIZE,
542 data += ARCTWO_BLOCK_SIZE)
544 char tmpIV[ARCTWO_BLOCK_SIZE];
546 memcpy (tmpIV, data, ARCTWO_BLOCK_SIZE);
547 arctwo_decrypt (&ctx->arctwoContext, data, data,
549 for (i = 0; i < ARCTWO_BLOCK_SIZE; i++)
550 data[i] ^= ctx->arctwoIV[i];
551 memcpy (ctx->arctwoIV, tmpIV, ARCTWO_BLOCK_SIZE);
556 return GC_INVALID_CIPHER;
561 #ifdef GNULIB_GC_ARCFOUR
564 arcfour_stream (&ctx->arcfourContext, data, data, len);
570 for (; len >= 8; len -= 8, data += 8)
571 gl_des_ecb_decrypt (&ctx->desContext, data, data);
575 #ifdef GNULIB_GC_RIJNDAEL
582 nblocks = rijndaelBlockDecrypt (&ctx->aesContext, &ctx->aesDecKey,
583 data, 8 * len, data);
585 return GC_INVALID_CIPHER;
591 return GC_INVALID_CIPHER;
598 gc_cipher_close (gc_cipher_handle handle)
600 _gc_cipher_ctx *ctx = handle;
609 #define MAX_DIGEST_SIZE 20
611 typedef struct _gc_hash_ctx
615 char hash[MAX_DIGEST_SIZE];
617 struct md2_ctx md2Context;
620 struct md4_ctx md4Context;
623 struct md5_ctx md5Context;
625 #ifdef GNULIB_GC_SHA1
626 struct sha1_ctx sha1Context;
631 gc_hash_open (Gc_hash hash, Gc_hash_mode mode, gc_hash_handle * outhandle)
636 ctx = calloc (sizeof (*ctx), 1);
638 return GC_MALLOC_ERROR;
647 md2_init_ctx (&ctx->md2Context);
653 md4_init_ctx (&ctx->md4Context);
659 md5_init_ctx (&ctx->md5Context);
663 #ifdef GNULIB_GC_SHA1
665 sha1_init_ctx (&ctx->sha1Context);
670 rc = GC_INVALID_HASH;
680 rc = GC_INVALID_HASH;
693 gc_hash_clone (gc_hash_handle handle, gc_hash_handle * outhandle)
695 _gc_hash_ctx *in = handle;
698 *outhandle = out = calloc (sizeof (*out), 1);
700 return GC_MALLOC_ERROR;
702 memcpy (out, in, sizeof (*out));
708 gc_hash_digest_length (Gc_hash hash)
715 len = GC_MD2_DIGEST_SIZE;
719 len = GC_MD4_DIGEST_SIZE;
723 len = GC_MD5_DIGEST_SIZE;
727 len = GC_RMD160_DIGEST_SIZE;
731 len = GC_SHA1_DIGEST_SIZE;
742 gc_hash_write (gc_hash_handle handle, size_t len, const char *data)
744 _gc_hash_ctx *ctx = handle;
750 md2_process_bytes (data, len, &ctx->md2Context);
756 md4_process_bytes (data, len, &ctx->md4Context);
762 md5_process_bytes (data, len, &ctx->md5Context);
766 #ifdef GNULIB_GC_SHA1
768 sha1_process_bytes (data, len, &ctx->sha1Context);
778 gc_hash_read (gc_hash_handle handle)
780 _gc_hash_ctx *ctx = handle;
781 const char *ret = NULL;
787 md2_finish_ctx (&ctx->md2Context, ctx->hash);
794 md4_finish_ctx (&ctx->md4Context, ctx->hash);
801 md5_finish_ctx (&ctx->md5Context, ctx->hash);
806 #ifdef GNULIB_GC_SHA1
808 sha1_finish_ctx (&ctx->sha1Context, ctx->hash);
821 gc_hash_close (gc_hash_handle handle)
823 _gc_hash_ctx *ctx = handle;
829 gc_hash_buffer (Gc_hash hash, const void *in, size_t inlen, char *resbuf)
835 md2_buffer (in, inlen, resbuf);
841 md4_buffer (in, inlen, resbuf);
847 md5_buffer (in, inlen, resbuf);
851 #ifdef GNULIB_GC_SHA1
853 sha1_buffer (in, inlen, resbuf);
858 return GC_INVALID_HASH;
866 gc_md2 (const void *in, size_t inlen, void *resbuf)
868 md2_buffer (in, inlen, resbuf);
875 gc_md4 (const void *in, size_t inlen, void *resbuf)
877 md4_buffer (in, inlen, resbuf);
884 gc_md5 (const void *in, size_t inlen, void *resbuf)
886 md5_buffer (in, inlen, resbuf);
891 #ifdef GNULIB_GC_SHA1
893 gc_sha1 (const void *in, size_t inlen, void *resbuf)
895 sha1_buffer (in, inlen, resbuf);
900 #ifdef GNULIB_GC_HMAC_MD5
902 gc_hmac_md5 (const void *key, size_t keylen,
903 const void *in, size_t inlen, char *resbuf)
905 hmac_md5 (key, keylen, in, inlen, resbuf);
910 #ifdef GNULIB_GC_HMAC_SHA1
912 gc_hmac_sha1 (const void *key, size_t keylen,
913 const void *in, size_t inlen, char *resbuf)
915 hmac_sha1 (key, keylen, in, inlen, resbuf);