=================================================================== RCS file: /cvsrepo/anoncvs/cvs/src/usr.bin/openssl/rand.c,v retrieving revision 1.1 retrieving revision 1.2 diff -u -r1.1 -r1.2 --- src/usr.bin/openssl/rand.c 2014/08/26 17:47:25 1.1 +++ src/usr.bin/openssl/rand.c 2014/08/27 14:59:44 1.2 @@ -1,4 +1,4 @@ -/* $OpenBSD: rand.c,v 1.1 2014/08/26 17:47:25 jsing Exp $ */ +/* $OpenBSD: rand.c,v 1.2 2014/08/27 14:59:44 jsing Exp $ */ /* ==================================================================== * Copyright (c) 1998-2001 The OpenSSL Project. All rights reserved. * @@ -63,123 +63,124 @@ #include #include -/* -out file - write to file - * -base64 - base64 encode output - * -hex - hex encode output - * num - write 'num' bytes - */ +struct { + int base64; + char *engine; + int hex; + char *outfile; +} rand_config; +struct option rand_options[] = { + { + .name = "base64", + .desc = "Perform base64 encoding on output", + .type = OPTION_FLAG, + .opt.flag = &rand_config.base64, + }, +#ifndef OPENSSL_NO_ENGINE + { + .name = "engine", + .argname = "id", + .desc = "Use the engine specified by the given identifier", + .type = OPTION_ARG, + .opt.arg = &rand_config.engine, + }, +#endif + { + .name = "hex", + .desc = "Hexadecimal output", + .type = OPTION_FLAG, + .opt.flag = &rand_config.hex, + }, + { + .name = "out", + .argname = "file", + .desc = "Write to the given file instead of standard output", + .type = OPTION_ARG, + .opt.arg = &rand_config.outfile, + }, + {}, +}; + +static void +rand_usage() +{ + fprintf(stderr, + "usage: rand [-base64 | -hex] [-engine id] [-out file] num\n"); + options_usage(rand_options); +} + int rand_main(int, char **); int rand_main(int argc, char **argv) { - int i, r, ret = 1; - int badopt; - char *outfile = NULL; - int base64 = 0; - int hex = 0; - BIO *out = NULL; + char *num_bytes = NULL; + int ret = 1; + int badopt = 0; int num = -1; -#ifndef OPENSSL_NO_ENGINE - char *engine = NULL; -#endif + int i, r; + BIO *out = NULL; - badopt = 0; - i = 0; - while (!badopt && argv[++i] != NULL) { - if (strcmp(argv[i], "-out") == 0) { - if ((argv[i + 1] != NULL) && (outfile == NULL)) - outfile = argv[++i]; - else - badopt = 1; - } -#ifndef OPENSSL_NO_ENGINE - else if (strcmp(argv[i], "-engine") == 0) { - if ((argv[i + 1] != NULL) && (engine == NULL)) - engine = argv[++i]; - else - badopt = 1; - } -#endif - else if (strcmp(argv[i], "-base64") == 0) { - if (!base64) - base64 = 1; - else - badopt = 1; - } else if (strcmp(argv[i], "-hex") == 0) { - if (!hex) - hex = 1; - else - badopt = 1; - } else if (isdigit((unsigned char) argv[i][0])) { - if (num < 0) { - r = sscanf(argv[i], "%d", &num); - if (r == 0 || num < 0) - badopt = 1; - } else - badopt = 1; - } else - badopt = 1; + if (options_parse(argc, argv, rand_options, &num_bytes) != 0) { + rand_usage(); + return (1); } - if (hex && base64) + if (num_bytes != NULL) { + r = sscanf(num_bytes, "%d", &num); + if (r == 0 || num < 0) + badopt = 1; + } else badopt = 1; - if (num < 0) + if (rand_config.hex && rand_config.base64) badopt = 1; if (badopt) { - BIO_printf(bio_err, "Usage: rand [options] num\n"); - BIO_printf(bio_err, "where options are\n"); - BIO_printf(bio_err, "-out file - write to file\n"); -#ifndef OPENSSL_NO_ENGINE - BIO_printf(bio_err, "-engine e - use engine e, possibly a hardware device.\n"); -#endif - BIO_printf(bio_err, "-base64 - base64 encode output\n"); - BIO_printf(bio_err, "-hex - hex encode output\n"); + rand_usage(); goto err; } + #ifndef OPENSSL_NO_ENGINE - setup_engine(bio_err, engine, 0); + setup_engine(bio_err, rand_config.engine, 0); #endif out = BIO_new(BIO_s_file()); if (out == NULL) goto err; - if (outfile != NULL) - r = BIO_write_filename(out, outfile); - else { + if (rand_config.outfile != NULL) + r = BIO_write_filename(out, rand_config.outfile); + else r = BIO_set_fp(out, stdout, BIO_NOCLOSE | BIO_FP_TEXT); - } if (r <= 0) goto err; - - if (base64) { + if (rand_config.base64) { BIO *b64 = BIO_new(BIO_f_base64()); if (b64 == NULL) goto err; out = BIO_push(b64, out); } + while (num > 0) { unsigned char buf[4096]; int chunk; chunk = num; if (chunk > (int) sizeof(buf)) - chunk = sizeof buf; + chunk = sizeof(buf); r = RAND_bytes(buf, chunk); if (r <= 0) goto err; - if (!hex) - BIO_write(out, buf, chunk); - else { + if (rand_config.hex) { for (i = 0; i < chunk; i++) BIO_printf(out, "%02x", buf[i]); - } + } else + BIO_write(out, buf, chunk); num -= chunk; } - if (hex) + + if (rand_config.hex) BIO_puts(out, "\n"); (void) BIO_flush(out);