summaryrefslogtreecommitdiff
path: root/plugins/MirOTR/Libgcrypt/random/random-fips.c
diff options
context:
space:
mode:
Diffstat (limited to 'plugins/MirOTR/Libgcrypt/random/random-fips.c')
-rw-r--r--plugins/MirOTR/Libgcrypt/random/random-fips.c175
1 files changed, 93 insertions, 82 deletions
diff --git a/plugins/MirOTR/Libgcrypt/random/random-fips.c b/plugins/MirOTR/Libgcrypt/random/random-fips.c
index 2667e71fd8..d00825e2a1 100644
--- a/plugins/MirOTR/Libgcrypt/random/random-fips.c
+++ b/plugins/MirOTR/Libgcrypt/random/random-fips.c
@@ -72,7 +72,7 @@
integer variable is only used to check the locking state; that is,
it is not meant to be thread-safe but merely as a failsafe feature
to assert proper locking. */
-static ath_mutex_t fips_rng_lock = ATH_MUTEX_INITIALIZER;
+static ath_mutex_t fips_rng_lock;
static int fips_rng_is_locked;
@@ -135,7 +135,7 @@ struct rng_context
unsigned char guard_2[1];
- /* The last result from the x931_aes fucntion. Only valid if
+ /* The last result from the x931_aes function. Only valid if
compare_value_valid is set. */
unsigned char compare_value[16];
@@ -157,7 +157,7 @@ struct rng_context
/* We need to keep track of the process which did the initialization
so that we can detect a fork. The volatile modifier is required
so that the compiler does not optimize it away in case the getpid
- function is badly attributed. */
+ function is badly attributed. */
pid_t key_init_pid;
pid_t seed_init_pid;
};
@@ -192,7 +192,7 @@ basic_initialization (void)
static int initialized;
int my_errno;
- if (!initialized)
+ if (initialized)
return;
initialized = 1;
@@ -200,10 +200,10 @@ basic_initialization (void)
if (my_errno)
log_fatal ("failed to create the RNG lock: %s\n", strerror (my_errno));
fips_rng_is_locked = 0;
-
+
/* Make sure that we are still using the values we have
traditionally used for the random levels. */
- gcry_assert (GCRY_WEAK_RANDOM == 0
+ gcry_assert (GCRY_WEAK_RANDOM == 0
&& GCRY_STRONG_RANDOM == 1
&& GCRY_VERY_STRONG_RANDOM == 2);
@@ -262,7 +262,7 @@ check_guards (rng_context_t rng_ctx)
timestamp we construct is made up the real time and three counters:
Buffer: 00112233445566778899AABBCCDDEEFF
- !--+---!!-+-!!+!!--+---!!--+---!
+ !--+---!!-+-!!+!!--+---!!--+---!
seconds ---------/ | | | |
microseconds -----------/ | | |
counter2 -------------------/ | |
@@ -272,7 +272,7 @@ check_guards (rng_context_t rng_ctx)
Counter 2 is just 12 bits wide and used to track fractions of
milliseconds whereas counters 1 and 0 are combined to a free
running 64 bit counter. */
-static void
+static void
x931_get_dt (unsigned char *buffer, size_t length, rng_context_t rng_ctx)
{
gcry_assert (length == 16); /* This length is required for use with AES. */
@@ -281,7 +281,7 @@ x931_get_dt (unsigned char *buffer, size_t length, rng_context_t rng_ctx)
/* If the random context indicates that a test DT should be used,
take the DT value from the context. For safety reasons we do
this only if the context is not one of the regular contexts. */
- if (rng_ctx->test_dt_ptr
+ if (rng_ctx->test_dt_ptr
&& rng_ctx != nonce_context
&& rng_ctx != std_rng_context
&& rng_ctx != strong_rng_context)
@@ -301,7 +301,7 @@ x931_get_dt (unsigned char *buffer, size_t length, rng_context_t rng_ctx)
static u32 last_sec, last_usec;
static u32 counter1, counter0;
static u16 counter2;
-
+
unsigned int usec;
struct timeval tv;
@@ -350,11 +350,11 @@ x931_get_dt (unsigned char *buffer, size_t length, rng_context_t rng_ctx)
/* Add the free running counter. */
buffer[8] = ((counter1 >> 24) & 0xff);
buffer[9] = ((counter1 >> 16) & 0xff);
- buffer[10] = ((counter1 >> 8) & 0xff);
+ buffer[10] = ((counter1 >> 8) & 0xff);
buffer[11] = ((counter1) & 0xff);
buffer[12] = ((counter0 >> 24) & 0xff);
buffer[13] = ((counter0 >> 16) & 0xff);
- buffer[14] = ((counter0 >> 8) & 0xff);
+ buffer[14] = ((counter0 >> 8) & 0xff);
buffer[15] = ((counter0) & 0xff);
/* Bump up that counter. */
if (!++counter0)
@@ -372,7 +372,7 @@ x931_get_dt (unsigned char *buffer, size_t length, rng_context_t rng_ctx)
the result at R. R needs to be provided by the caller with a size
of at least LENGTH bytes. */
static void
-xor_buffer (unsigned char *r,
+xor_buffer (unsigned char *r,
const unsigned char *a, const unsigned char *b, size_t length)
{
for ( ; length; length--, a++, b++, r++)
@@ -383,16 +383,16 @@ xor_buffer (unsigned char *r,
/* Encrypt LENGTH bytes of INPUT to OUTPUT using KEY. LENGTH
needs to be 16. */
static void
-encrypt_aes (gcry_cipher_hd_t key,
+encrypt_aes (gcry_cipher_hd_t key,
unsigned char *output, const unsigned char *input, size_t length)
{
gpg_error_t err;
gcry_assert (length == 16);
- err = gcry_cipher_encrypt (key, output, length, input, length);
+ err = _gcry_cipher_encrypt (key, output, length, input, length);
if (err)
- log_fatal ("AES encryption in RNG failed: %s\n", gcry_strerror (err));
+ log_fatal ("AES encryption in RNG failed: %s\n", _gcry_strerror (err));
}
@@ -406,7 +406,7 @@ encrypt_aes (gcry_cipher_hd_t key,
On return the result is stored at RESULT_R and the SEED_V is
updated. May only be used while holding the lock. */
static void
-x931_aes (unsigned char result_R[16],
+x931_aes (unsigned char result_R[16],
unsigned char datetime_DT[16], unsigned char seed_V[16],
gcry_cipher_hd_t key,
unsigned char intermediate_I[16], unsigned char temp_xor[16])
@@ -415,7 +415,7 @@ x931_aes (unsigned char result_R[16],
Let V be a 128-bit seed value which is also kept secret, and XOR
be the exclusive-or operator. Let DT be a date/time vector which
- is updated on each iteration. I is a intermediate value.
+ is updated on each iteration. I is a intermediate value.
I = ede*K(DT) */
encrypt_aes (key, intermediate_I, datetime_DT, 16);
@@ -509,7 +509,7 @@ x931_aes_driver (unsigned char *output, size_t length, rng_context_t rng_ctx)
}
memcpy (rng_ctx->compare_value, result_buffer, 16);
}
-
+
/* Append to outbut. */
memcpy (output, result_buffer, nbytes);
wipememory (result_buffer, 16);
@@ -555,7 +555,7 @@ get_entropy (size_t nbytes)
int rc;
gcry_assert (!entropy_collect_buffer);
- entropy_collect_buffer = gcry_xmalloc_secure (nbytes);
+ entropy_collect_buffer = xmalloc_secure (nbytes);
entropy_collect_buffer_size = nbytes;
entropy_collect_buffer_len = 0;
@@ -564,7 +564,7 @@ get_entropy (size_t nbytes)
X931_AES_KEYLEN,
GCRY_VERY_STRONG_RANDOM);
#elif USE_RNDW32
- do
+ do
{
rc = _gcry_rndw32_gather_random (entropy_collect_cb, 0,
X931_AES_KEYLEN,
@@ -577,7 +577,7 @@ get_entropy (size_t nbytes)
if (rc < 0 || entropy_collect_buffer_len != entropy_collect_buffer_size)
{
- gcry_free (entropy_collect_buffer);
+ xfree (entropy_collect_buffer);
entropy_collect_buffer = NULL;
log_fatal ("error getting entropy data\n");
}
@@ -595,25 +595,25 @@ static gcry_cipher_hd_t
x931_generate_key (int for_nonce)
{
gcry_cipher_hd_t hd;
- gpg_error_t err;
+ gpg_err_code_t rc;
void *buffer;
gcry_assert (fips_rng_is_locked);
/* Allocate a cipher context. */
- err = gcry_cipher_open (&hd, GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_ECB,
+ rc = _gcry_cipher_open (&hd, GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_ECB,
GCRY_CIPHER_SECURE);
- if (err)
+ if (rc)
{
log_error ("error creating cipher context for RNG: %s\n",
- gcry_strerror (err));
+ _gcry_strerror (rc));
return NULL;
}
/* Get a key from the standard RNG or from the entropy source. */
if (for_nonce)
{
- buffer = gcry_xmalloc (X931_AES_KEYLEN);
+ buffer = xmalloc (X931_AES_KEYLEN);
get_random (buffer, X931_AES_KEYLEN, std_rng_context);
}
else
@@ -623,13 +623,13 @@ x931_generate_key (int for_nonce)
/* Set the key and delete the buffer because the key is now part of
the cipher context. */
- err = gcry_cipher_setkey (hd, buffer, X931_AES_KEYLEN);
+ rc = _gcry_cipher_setkey (hd, buffer, X931_AES_KEYLEN);
wipememory (buffer, X931_AES_KEYLEN);
- gcry_free (buffer);
- if (err)
+ xfree (buffer);
+ if (rc)
{
- log_error ("error creating key for RNG: %s\n", gcry_strerror (err));
- gcry_cipher_close (hd);
+ log_error ("error creating key for RNG: %s\n", _gcry_strerror (rc));
+ _gcry_cipher_close (hd);
return NULL;
}
@@ -651,7 +651,7 @@ x931_generate_seed (unsigned char *seed_buffer, size_t length)
memcpy (seed_buffer, buffer, X931_AES_KEYLEN);
wipememory (buffer, X931_AES_KEYLEN);
- gcry_free (buffer);
+ xfree (buffer);
}
@@ -753,17 +753,17 @@ _gcry_rngfips_initialize (int full)
if (!tempvalue_for_x931_aes_driver)
{
tempvalue_for_x931_aes_driver
- = gcry_xmalloc_secure (TEMPVALUE_FOR_X931_AES_DRIVER_SIZE);
+ = xmalloc_secure (TEMPVALUE_FOR_X931_AES_DRIVER_SIZE);
/* Allocate the random contexts. Note that we do not need to use
secure memory for the nonce context. */
- nonce_context = gcry_xcalloc (1, sizeof *nonce_context);
+ nonce_context = xcalloc (1, sizeof *nonce_context);
setup_guards (nonce_context);
- std_rng_context = gcry_xcalloc_secure (1, sizeof *std_rng_context);
+ std_rng_context = xcalloc_secure (1, sizeof *std_rng_context);
setup_guards (std_rng_context);
-
- strong_rng_context = gcry_xcalloc_secure (1, sizeof *strong_rng_context);
+
+ strong_rng_context = xcalloc_secure (1, sizeof *strong_rng_context);
setup_guards (strong_rng_context);
}
else
@@ -780,6 +780,19 @@ _gcry_rngfips_initialize (int full)
}
+/* Try to close the FDs of the random gather module. This is
+ currently only implemented for rndlinux. */
+void
+_gcry_rngfips_close_fds (void)
+{
+ lock_rng ();
+#if USE_RNDLINUX
+ _gcry_rndlinux_gather_random (NULL, 0, 0, 0);
+#endif
+ unlock_rng ();
+}
+
+
/* Print some statistics about the RNG. */
void
_gcry_rngfips_dump_stats (void)
@@ -807,9 +820,9 @@ _gcry_rngfips_add_bytes (const void *buf, size_t buflen, int quality)
(void)buflen;
(void)quality;
return 0; /* Not implemented. */
-}
+}
+
-
/* Public function to fill the buffer with LENGTH bytes of
cryptographically strong random bytes. Level GCRY_WEAK_RANDOM is
here mapped to GCRY_STRONG_RANDOM, GCRY_STRONG_RANDOM is strong
@@ -820,7 +833,7 @@ _gcry_rngfips_randomize (void *buffer, size_t length,
enum gcry_random_level level)
{
_gcry_rngfips_initialize (1); /* Auto-initialize if needed. */
-
+
lock_rng ();
if (level == GCRY_VERY_STRONG_RANDOM)
get_random (buffer, length, strong_rng_context);
@@ -850,7 +863,7 @@ _gcry_rngfips_create_nonce (void *buffer, size_t length)
static gcry_err_code_t
selftest_kat (selftest_report_func_t report)
{
- static struct
+ static struct
{
const unsigned char key[16];
const unsigned char dt[16];
@@ -880,7 +893,7 @@ selftest_kat (selftest_report_func_t report)
0x13, 0xd3, 0x13, 0xfa, 0x20, 0xe9, 0x8d, 0xbc },
{ 0xc8, 0xd1, 0xe5, 0x11, 0x59, 0x52, 0xf7, 0xfa,
0x37, 0x38, 0xb4, 0xc5, 0xce, 0xb2, 0xb0, 0x9a },
- { 0x0d, 0x9c, 0xc5, 0x0d, 0x16, 0xe1, 0xbc, 0xed,
+ { 0x0d, 0x9c, 0xc5, 0x0d, 0x16, 0xe1, 0xbc, 0xed,
0xcf, 0x60, 0x62, 0x09, 0x9d, 0x20, 0x83, 0x7e } } },
{ { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f },
@@ -892,50 +905,50 @@ selftest_kat (selftest_report_func_t report)
0x63, 0x19, 0x37, 0x6f, 0x15, 0x22, 0x57, 0x56 },
{ 0x7a, 0x14, 0x76, 0x77, 0x95, 0x17, 0x7e, 0xc8,
0x92, 0xe8, 0xdd, 0x15, 0xcb, 0x1f, 0xbc, 0xb1 },
- { 0x25, 0x3e, 0x2e, 0xa2, 0x41, 0x1b, 0xdd, 0xf5,
+ { 0x25, 0x3e, 0x2e, 0xa2, 0x41, 0x1b, 0xdd, 0xf5,
0x21, 0x48, 0x41, 0x71, 0xb3, 0x8d, 0x2f, 0x4c } } }
};
int tvidx, ridx;
rng_context_t test_ctx;
- gpg_error_t err;
+ gpg_err_code_t rc;
const char *errtxt = NULL;
unsigned char result[16];
gcry_assert (tempvalue_for_x931_aes_driver);
- test_ctx = gcry_xcalloc (1, sizeof *test_ctx);
+ test_ctx = xcalloc (1, sizeof *test_ctx);
setup_guards (test_ctx);
-
+
lock_rng ();
for (tvidx=0; tvidx < DIM (tv); tvidx++)
{
/* Setup the key. */
- err = gcry_cipher_open (&test_ctx->cipher_hd,
+ rc = _gcry_cipher_open (&test_ctx->cipher_hd,
GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_ECB,
GCRY_CIPHER_SECURE);
- if (err)
+ if (rc)
{
errtxt = "error creating cipher context for RNG";
goto leave;
}
- err = gcry_cipher_setkey (test_ctx->cipher_hd, tv[tvidx].key, 16);
- if (err)
+ rc = _gcry_cipher_setkey (test_ctx->cipher_hd, tv[tvidx].key, 16);
+ if (rc)
{
errtxt = "error setting key for RNG";
goto leave;
}
test_ctx->key_init_pid = getpid ();
-
+
/* Setup the seed. */
memcpy (test_ctx->seed_V, tv[tvidx].v, 16);
test_ctx->is_seeded = 1;
test_ctx->seed_init_pid = getpid ();
-
+
/* Setup a DT value. */
test_ctx->test_dt_ptr = tv[tvidx].dt;
- test_ctx->test_dt_counter = ( (tv[tvidx].dt[12] << 24)
+ test_ctx->test_dt_counter = ( (tv[tvidx].dt[12] << 24)
|(tv[tvidx].dt[13] << 16)
|(tv[tvidx].dt[14] << 8)
|(tv[tvidx].dt[15]) );
@@ -949,7 +962,7 @@ selftest_kat (selftest_report_func_t report)
errtxt = "X9.31 RNG core function failed";
goto leave;
}
-
+
/* Compare it to the known value. */
if (memcmp (result, tv[tvidx].r[ridx], 16))
{
@@ -969,7 +982,7 @@ selftest_kat (selftest_report_func_t report)
goto leave;
}
- gcry_cipher_close (test_ctx->cipher_hd);
+ _gcry_cipher_close (test_ctx->cipher_hd);
test_ctx->cipher_hd = NULL;
test_ctx->is_seeded = 0;
check_guards (test_ctx);
@@ -977,9 +990,9 @@ selftest_kat (selftest_report_func_t report)
leave:
unlock_rng ();
- gcry_cipher_close (test_ctx->cipher_hd);
+ _gcry_cipher_close (test_ctx->cipher_hd);
check_guards (test_ctx);
- gcry_free (test_ctx);
+ xfree (test_ctx);
if (report && errtxt)
report ("random", 0, "KAT", errtxt);
return errtxt? GPG_ERR_SELFTEST_FAILED : 0;
@@ -997,10 +1010,10 @@ _gcry_rngfips_selftest (selftest_report_func_t report)
char buffer[8];
/* Do a simple test using the public interface. This will also
- enforce full intialization of the RNG. We need to be fully
+ enforce full initialization of the RNG. We need to be fully
initialized due to the global requirement of the
tempvalue_for_x931_aes_driver stuff. */
- gcry_randomize (buffer, sizeof buffer, GCRY_STRONG_RANDOM);
+ _gcry_randomize (buffer, sizeof buffer, GCRY_STRONG_RANDOM);
}
ec = selftest_kat (report);
@@ -1022,46 +1035,46 @@ _gcry_rngfips_init_external_test (void **r_context, unsigned int flags,
const void *seed, size_t seedlen,
const void *dt, size_t dtlen)
{
- gpg_error_t err;
+ gpg_err_code_t rc;
rng_context_t test_ctx;
_gcry_rngfips_initialize (1); /* Auto-initialize if needed. */
-
+
if (!r_context
- || !key || keylen != 16
+ || !key || keylen != 16
|| !seed || seedlen != 16
|| !dt || dtlen != 16 )
return GPG_ERR_INV_ARG;
- test_ctx = gcry_calloc (1, sizeof *test_ctx + dtlen);
+ test_ctx = xtrycalloc (1, sizeof *test_ctx + dtlen);
if (!test_ctx)
return gpg_err_code_from_syserror ();
setup_guards (test_ctx);
-
+
/* Setup the key. */
- err = gcry_cipher_open (&test_ctx->cipher_hd,
+ rc = _gcry_cipher_open (&test_ctx->cipher_hd,
GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_ECB,
GCRY_CIPHER_SECURE);
- if (err)
+ if (rc)
goto leave;
- err = gcry_cipher_setkey (test_ctx->cipher_hd, key, keylen);
- if (err)
+ rc = _gcry_cipher_setkey (test_ctx->cipher_hd, key, keylen);
+ if (rc)
goto leave;
test_ctx->key_init_pid = getpid ();
-
+
/* Setup the seed. */
memcpy (test_ctx->seed_V, seed, seedlen);
test_ctx->is_seeded = 1;
test_ctx->seed_init_pid = getpid ();
-
+
/* Setup a DT value. Because our context structure only stores a
pointer we copy the DT value to the extra space we allocated in
the test_ctx and set the pointer to that address. */
memcpy ((unsigned char*)test_ctx + sizeof *test_ctx, dt, dtlen);
- test_ctx->test_dt_ptr = (unsigned char*)test_ctx + sizeof *test_ctx;
- test_ctx->test_dt_counter = ( (test_ctx->test_dt_ptr[12] << 24)
+ test_ctx->test_dt_ptr = (unsigned char*)test_ctx + sizeof *test_ctx;
+ test_ctx->test_dt_counter = ( (test_ctx->test_dt_ptr[12] << 24)
|(test_ctx->test_dt_ptr[13] << 16)
|(test_ctx->test_dt_ptr[14] << 8)
|(test_ctx->test_dt_ptr[15]) );
@@ -1071,18 +1084,18 @@ _gcry_rngfips_init_external_test (void **r_context, unsigned int flags,
check_guards (test_ctx);
/* All fine. */
- err = 0;
+ rc = 0;
leave:
- if (err)
+ if (rc)
{
- gcry_cipher_close (test_ctx->cipher_hd);
- gcry_free (test_ctx);
+ _gcry_cipher_close (test_ctx->cipher_hd);
+ xfree (test_ctx);
*r_context = NULL;
}
else
*r_context = test_ctx;
- return gcry_err_code (err);
+ return rc;
}
@@ -1110,9 +1123,7 @@ _gcry_rngfips_deinit_external_test (void *context)
if (test_ctx)
{
- gcry_cipher_close (test_ctx->cipher_hd);
- gcry_free (test_ctx);
+ _gcry_cipher_close (test_ctx->cipher_hd);
+ xfree (test_ctx);
}
}
-
-