RSA BSAFE Crypto-C

Cryptographic Components for C

Search

x931rand.c

/* $Id: x931rand.c,v 1.6 2004/12/03 02:08:34 sparki Exp $ */
/* 
 * Copyright (C) 1998-2004 RSA Security Inc.
 *
 * This file shall only be used to demonstrate how to interface to an
 * RSA Security Inc. licensed development product.
 *
 * You have a royalty-free right to use, reproduce and distribute this
 * demonstration file, provided that you agree that RSA Security Inc.
 * has no warranty, implied or otherwise, or liability for this
 * demonstration file (including any modified version).  This software
 * is provided "as is" without warranties or representations of any
 * kind. RSA Security disclaims all conditions and warranties, statutory
 * and otherwise, both express and implied, with respect to the software,
 * its quality and performance, including but not limited to, all 
 * implied warranties of merchantability, fitness for a particular 
 * purpose, title and noninfringement of third party rights. Without 
 * limiting the foregoing, RSA Security does not warrant that the 
 * software is error-free or that errors in the product will be 
 * corrected. You agree that RSA Security shall not be liable for any
 * direct, indirect, incidental, special, consequential, punitive or
 * other damages whatsoever resulting from your use of this software
 * or any modified version.
 * 
 *
 */

#include "bsafe.h"
#include "demoutil.h"  /* in samples/common/include */

#define NUMBER_OF_RANDOM_BYTES 128
#define MAX_SEED_BYTES 385

B_ALGORITHM_METHOD *RANDOM_CHOOSER[] = {
  &AM_X931_RANDOM,
  (B_ALGORITHM_METHOD *)NULL_PTR
/* This will fix a problem that the IA64 compiler finds when *
 * seeing a short chooser list */
#ifdef IA64_FORCE_LARGE
                IA64_FORCE_LARGE
#endif
};

#ifdef CRYPTOC_APP
#define MAIN x931randomMain
#else
#define MAIN main
#endif

int MAIN(int argc, char *argv[])
{
  B_ALGORITHM_OBJ randomAlgorithm = (B_ALGORITHM_OBJ)NULL_PTR;
  A_X931_RANDOM_PARAMS x931Params;

  ITEM randomSeed = {NULL, 0};
  unsigned int minSeedLen;
  unsigned char randomByteBuffer[NUMBER_OF_RANDOM_BYTES];

  int status;

  do {
    /* The RSA_* demo code utilities are described in
       common/include/demoutil.h.  This procedure simply checks the
       command-line arguments for input or output options. */
    if ((status = RSA_SetOptions (argc, argv)) != 0)
      break;

    RSA_PrintMessage ("Generating random bytes\n");
    RSA_PrintMessage ("=======================\n");

    /* Create a random algorithm object */
    if ((status = B_CreateAlgorithmObject (&randomAlgorithm)) != 0)
      break;

    /* Set the random algorithm object to use AI_X931Random.
       Before we can call B_SetAlgorithmInfo, we need to prepare the
       X9.31 parameters.  The A_X931_RANDOM_PARAMS structure
       contains two parameters:  the number of independent streams
       of randomness and an ITEM containing random seed data to be
       divided up among the streams. */

    /* Set the number of streams in the A_X931_RANDOM_PARAMS
       structure. */
    x931Params.numberOfStreams = 6;

    /* In order to obtain a seed, we need to allocate space for it,
       and then request it from the user.  Note that the following
       method of seed gathering is insecure.  A real application would
       use a more secure method of seed gathering to ensure the
       security of the application.  */
    randomSeed.data = T_malloc (MAX_SEED_BYTES);
    if (randomSeed.data == NULL_PTR) {
      status = RSA_DEMO_E_ALLOC;
      break;
    }

    minSeedLen = 20 * x931Params.numberOfStreams;

    /* Prompt the user for input until enough seed data is provided */
    randomSeed.len = 0;
    do {
      RSA_PrintMessage ("We need at least %d bytes of random seed data.\n",
                        minSeedLen - randomSeed.len);
      RSA_PrintMessage ("Enter a random seed (%d bytes maximum): ",
                        MAX_SEED_BYTES - 1 - randomSeed.len);
      RSA_GetCommand ((char *)randomSeed.data + randomSeed.len,
                      MAX_SEED_BYTES - randomSeed.len, NULL);
      randomSeed.len = T_strlen ((char *)randomSeed.data);

      RSA_PrintBuf ("Random Seed", randomSeed.data, randomSeed.len);

      x931Params.seed.data = randomSeed.data;
      x931Params.seed.len = randomSeed.len;

      /* Specify the operation and pass the parameters to the
         algorithm object */
      status = B_SetAlgorithmInfo (randomAlgorithm, AI_X931Random,
                                   (POINTER)&x931Params);

      /* Quit if the buffer is filled, whether or not status is 0 */
      if (randomSeed.len == MAX_SEED_BYTES - 1)
        break;
    } while (status == BE_ALGORITHM_INFO);

    if (status != 0)
      break;

    T_memset (randomSeed.data, 0, randomSeed.len);

    /*  Initialize the random algorithm. */
    if ((status = B_RandomInit (randomAlgorithm, RANDOM_CHOOSER,
                                (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    /*  Since the random seed has already been passed in via
        the x931Params structure, we do not have to call
        B_RandomUpdate(). */

    /*  Generate.  First, prepare a buffer for receiving the
        random bytes before calling B_GenerateRandomBytes.  */
    if ((status = B_GenerateRandomBytes (randomAlgorithm, randomByteBuffer,
                                         NUMBER_OF_RANDOM_BYTES,
                                         (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    RSA_PrintBuf ("Random Bytes", randomByteBuffer, NUMBER_OF_RANDOM_BYTES);

  } while (0);

  if (status != 0)
    RSA_PrintError ("x931rand", status);

  /*  Destroy all objects, and free all memory  */
  B_DestroyAlgorithmObject (&randomAlgorithm);
  T_memset (randomByteBuffer, 0, NUMBER_OF_RANDOM_BYTES);
  T_memset (randomSeed.data, 0, randomSeed.len);
  T_free (randomSeed.data);

  return (status);
} /*  end main  */

Copyright (c) 1999-2005 RSA Security Inc. All rights reserved. 068-001001-6210-001-000 - 6.2.1