diff options
author | Werner Koch <wk@gnupg.org> | 2008-09-16 07:48:25 +0000 |
---|---|---|
committer | Werner Koch <wk@gnupg.org> | 2008-09-16 07:48:25 +0000 |
commit | 2f1962593d4465b50ad7ec5781fa08cd44aec820 (patch) | |
tree | bb6d2d62c682038bc8f91d12b111f6f1709b9d4b /tests/fipsrngdrv.c | |
parent | d84a7e0d5ed00dc6f3c32e755f9cca5977487538 (diff) | |
download | libgcrypt-2f1962593d4465b50ad7ec5781fa08cd44aec820.tar.gz |
Finish FIPS random test driver.
Disable re-seeding if in test mode.
Diffstat (limited to 'tests/fipsrngdrv.c')
-rw-r--r-- | tests/fipsrngdrv.c | 150 |
1 files changed, 137 insertions, 13 deletions
diff --git a/tests/fipsrngdrv.c b/tests/fipsrngdrv.c index 6100f909..bda0bde4 100644 --- a/tests/fipsrngdrv.c +++ b/tests/fipsrngdrv.c @@ -24,11 +24,25 @@ #include <stdlib.h> #include <string.h> #include <stdarg.h> +#include <errno.h> +#include <ctype.h> +#ifndef HAVE_W32_SYSTEM +# include <signal.h> +#endif -#include "../src/gcrypt.h" +#include <gcrypt.h> #define PGM "fipsrngdrv" +#define my_isascii(c) (!((c) & 0x80)) +#define digitp(p) (*(p) >= '0' && *(p) <= '9') +#define hexdigitp(a) (digitp (a) \ + || (*(a) >= 'A' && *(a) <= 'F') \ + || (*(a) >= 'a' && *(a) <= 'f')) +#define xtoi_1(p) (*(p) <= '9'? (*(p)- '0'): \ + *(p) <= 'F'? (*(p)-'A'+10):(*(p)-'a'+10)) +#define xtoi_2(p) ((xtoi_1(p) * 16) + xtoi_1((p)+1)) + static void die (const char *format, ...) @@ -43,6 +57,37 @@ die (const char *format, ...) } +/* Convert STRING consisting of hex characters into its binary + representation and store that at BUFFER. BUFFER needs to be of + LENGTH bytes. The function checks that the STRING will convert + exactly to LENGTH bytes. The string is delimited by either end of + string or a white space character. The function returns -1 on + error or the length of the parsed string. */ +int +hex2bin (const char *string, void *buffer, size_t length) +{ + int i; + const char *s = string; + + for (i=0; i < length; ) + { + if (!hexdigitp (s) || !hexdigitp (s+1)) + return -1; /* Invalid hex digits. */ + ((unsigned char*)buffer)[i++] = xtoi_2 (s); + s += 2; + } + if (*s && (!my_isascii (*s) || !isspace (*s)) ) + return -1; /* Not followed by Nul or white space. */ + if (i != length) + return -1; /* Not of expected length. */ + if (*s) + s++; /* Skip the delimiter. */ + return s - string; +} + + + + static gcry_error_t init_external_test (void **r_context, unsigned int flags, @@ -81,36 +126,115 @@ print_buffer (const unsigned char *buffer, size_t length) int main (int argc, char **argv) { + int last_argc = -1; + int verbose = 0; + int binary = 0; + int loop = 0; + int progress = 0; + unsigned char key[16]; + unsigned char seed[16]; + unsigned char dt[16]; void *context; gpg_error_t err; - int block; unsigned char buffer[16]; - (void)argc; - (void)argv; + if (argc) + { argc--; argv++; } + while (argc && last_argc != argc ) + { + last_argc = argc; + if (!strcmp (*argv, "--")) + { + argc--; argv++; + break; + } + else if (!strcmp (*argv, "--verbose")) + { + verbose = 2; + argc--; argv++; + } + else if (!strcmp (*argv, "--binary")) + { + binary = 1; + argc--; argv++; + } + else if (!strcmp (*argv, "--loop")) + { + loop = 1; + argc--; argv++; + } + else if (!strcmp (*argv, "--progress")) + { + progress = 1; + argc--; argv++; + } + } + + if (!argc) + { + memcpy (key, "1234567890123456", 16); + memcpy (seed, "abcdefghijklmnop", 16); + memcpy (dt, "XXXXXXXXXXXXXXXX", 16); + } + else if (argc == 3) + { + if ( hex2bin (argv[0], key, 16) < 0 + || hex2bin (argv[1], seed, 16) < 0 + || hex2bin (argv[2], dt, 16) < 0 ) + die ("args are not 32 hex digits each\n"); + } + else + die ("invalid usage\n"); + +#ifndef HAVE_W32_SYSTEM + if (loop) + signal (SIGPIPE, SIG_IGN); +#endif + + gcry_control (GCRYCTL_SET_VERBOSITY, (int)verbose); gcry_control (GCRYCTL_FORCE_FIPS_MODE, 0); - if (!gcry_check_version (GCRYPT_VERSION)) + if (!gcry_check_version ("1.4.3")) die ("version mismatch\n"); gcry_control (GCRYCTL_DISABLE_SECMEM, 0); - gcry_control (GCRYCTL_SET_VERBOSITY, 2); gcry_control (GCRYCTL_INITIALIZATION_FINISHED, 0); - err = init_external_test (&context, 0, - "1234567890123456", 16, - "abcdefghijklmnop", 16, - "XXXXXXXXXXXXXXXX", 16); + err = init_external_test (&context, 0, key, 16, seed, 16, dt, 16); if (err) die ("init external test failed: %s\n", gpg_strerror (err)); - for (block=0; block < 10; block++) + do { err = run_external_test (context, buffer, sizeof buffer); if (err) die ("run external test failed: %s\n", gpg_strerror (err)); - print_buffer (buffer, sizeof buffer); - putchar ('\n'); + if (binary) + { + if (fwrite (buffer, 16, 1, stdout) != 1) + { +#ifndef HAVE_W32_SYSTEM + if (loop && errno == EPIPE) + break; +#endif + die ("writing output failed: %s\n", strerror (errno)); + } + fflush (stdout); + } + else + { + print_buffer (buffer, sizeof buffer); + putchar ('\n'); + } + if (progress) + { + putc ('.', stderr); + fflush (stderr); + } } + while (loop); + + if (progress) + putc ('\n', stderr); deinit_external_test (context); |