RSA BSAFE Crypto-C

Cryptographic Components for C

Search

keywrap.c

/* $Id: keywrap.c,v 1.7 2004/12/03 02:08:37 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.
 *
 *
 */

/*  This program will generate a RSA keypair.  It will then encrypt the
 *  private key with a symmetric key in PEM format that is compatible
 *  with SSL-C.
 */

#include "bsafe.h"
#include "demoutil.h"  /* in samples/common/include */
#include "bsfutil.h"   /* in samples/common/include */
#include "rsautil.h"   /* in samples/pkalg/rsa */

#define RSA_MODULUS_BITS 512
#define BLOCK_SIZE ((RSA_MODULUS_BITS + 7) / 8)
#define DES_BLOCK_SIZE 8
#define MAX_OUTPUT_LEN 2048
#define KEY_BYTES 24


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

int MAIN(int argc, char *argv[])
{
  B_ALGORITHM_METHOD *ENCRYPT_CHOOSER[] = {
    &AM_DES_EDE3_CBC_DECRYPT,
    &AM_DES_EDE3_CBC_ENCRYPT,
    (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

  };

  B_KEY_METHOD *KEY_WRAP_CHOOSER[] = {
    &KM_PKCS_RSA_PRIVATE_BER_KEY,
    (B_KEY_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

  };

  B_ALGORITHM_OBJ randomAlgorithm = (B_ALGORITHM_OBJ)NULL_PTR;
  B_ALGORITHM_OBJ keyWrapper = (B_ALGORITHM_OBJ)NULL_PTR;
  B_ALGORITHM_OBJ keyUnwrapper = (B_ALGORITHM_OBJ)NULL_PTR;

  B_KEY_OBJ publicKey = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ privateKey = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ unwrappedKey = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ symmetricKey = (B_KEY_OBJ)NULL_PTR;
  B_SSLC_KEY_WRAP_PARAMS keyWrapParams;

  unsigned char symmetricKeyData[KEY_BYTES];
  unsigned char ivBytes[DES_BLOCK_SIZE];
  unsigned char *wrappedKey;
  unsigned int wrappedKeyLen, maxOutLen;

  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 RSA Keypair\n");
    RSA_PrintMessage ("======================\n");

    if ((status = RSA_CreateRandomAlgorithmObject (&randomAlgorithm)) != 0)
      break;

    /* The following function is in samples/pkalg/rsa/rsautil.c */
    if ((status = RSA_CreateRSAKeypair
                    (&publicKey, &privateKey, RSA_MODULUS_BITS,
                     randomAlgorithm)) != 0)
      break;

    /*  Create the information for the symmetric key */
    if ((status = B_GenerateRandomBytes (randomAlgorithm, ivBytes,
                                         DES_BLOCK_SIZE,
                                         (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    if ((status = B_GenerateRandomBytes (randomAlgorithm, symmetricKeyData,
                                         KEY_BYTES,
                                         (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    if ((status = B_CreateKeyObject (&symmetricKey)) != 0)
      break;

    if ((status = B_SetKeyInfo (symmetricKey, KI_24Byte,
                                (POINTER)symmetricKeyData)) != 0)
      break;


    /*  Create the parameters for key wrapping */
    keyWrapParams.encryptAlgorithm = AI_DES_EDE3_CBCPadIV8;
    keyWrapParams.iv = T_malloc (DES_BLOCK_SIZE);
    keyWrapParams.pemEncode = 1;
    T_memcpy (keyWrapParams.iv, ivBytes, DES_BLOCK_SIZE);

    maxOutLen = MAX_OUTPUT_LEN;

    RSA_PrintMessage ("\nPerforming Key Wrapping\n");
    RSA_PrintMessage ("=======================\n");

    /*  Create an Algorithm Object */
    if ((status = B_CreateAlgorithmObject (&keyWrapper)) != 0)
      break;

    /*  Set the algorithm object to AI_SSLC_KeyWrap */
    if ((status = B_SetAlgorithmInfo (keyWrapper, AI_SSLC_KeyWrap,
                                      (POINTER)&keyWrapParams)) != 0)
      break;

    if ((status = B_WrapKeyInit (keyWrapper, symmetricKey, ENCRYPT_CHOOSER,
                                 (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    wrappedKey = (unsigned char *)T_malloc (MAX_OUTPUT_LEN);

    /*  Perform the key wrapping */
    if ((status = B_WrapKey (keyWrapper, wrappedKey, &wrappedKeyLen,
                             maxOutLen, privateKey, KEY_WRAP_CHOOSER,
                             randomAlgorithm,
                             (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    RSA_PrintBuf("The wrapped key ",wrappedKey, wrappedKeyLen);

    RSA_PrintMessage ("\nPerforming Key Unwrapping\n");
    RSA_PrintMessage ("=======================\n");

    /*  Create an Algorithm Object */
    if ((status = B_CreateAlgorithmObject (&keyUnwrapper)) != 0)
      break;

    /*  Create a Key Object to hold the unwrapped key */
    if ((status = B_CreateKeyObject(&unwrappedKey)) != 0)
      break;

    /*  Set the algorithm object to AI_SSLC_KeyWrap */
    if ((status = B_SetAlgorithmInfo (keyUnwrapper, AI_SSLC_KeyWrap,
                                      (POINTER )&keyWrapParams)) != 0)
      break;

    if ((status = B_UnwrapKeyInit (keyUnwrapper, symmetricKey, ENCRYPT_CHOOSER,
                                 (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    /* Perform the key unwrapping */
    if ((status = B_UnwrapKey (keyUnwrapper, unwrappedKey, wrappedKey,
                               wrappedKeyLen, KEY_WRAP_CHOOSER,
                               randomAlgorithm,
                               (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    RSA_PrintMessage ("Success!  \n");

  } while (0);

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

  /*  Destroy the key and algorithm objects  */
  B_DestroyAlgorithmObject (&randomAlgorithm);
  B_DestroyAlgorithmObject (&keyWrapper);
  B_DestroyAlgorithmObject (&keyUnwrapper);
  B_DestroyKeyObject (&unwrappedKey);
  B_DestroyKeyObject (&privateKey);
  B_DestroyKeyObject (&publicKey);
  B_DestroyKeyObject (&symmetricKey);

  if (wrappedKey != NULL) {
    T_free (wrappedKey);
  }

  if (keyWrapParams.iv != NULL) {
    T_free (keyWrapParams.iv);
  }

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

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