RSA BSAFE Crypto-C

Cryptographic Components for C

Search

alginfo.c

/* $Id: alginfo.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 */
#include "bsfutil.h"     /* in samples/common/include */
#include "alginfoutil.h" /* in samples/alginfo */
#include "rsautil.h"     /* in samples/pkalg/rsa */

#define KEY_SIZE 10      /* key size in bytes */
#define RSA_MODULUS_BITS 512

B_ALGORITHM_METHOD *RC4_CHOOSER[] = {
  &AM_RC4_ENCRYPT,
  &AM_RC4_DECRYPT,
  (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 alginfoMain
#else
#define MAIN main
#endif

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

  B_KEY_OBJ rc4Key = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ publicKey = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ privateKey = (B_KEY_OBJ)NULL_PTR;
  B_KEY_OBJ keyObject = (B_KEY_OBJ)NULL_PTR;

  ITEM rc4KeyItem = {NULL, 0};
  ITEM myPublicKeyBER = {NULL, 0};
  ITEM *cryptocPublicKeyBER = NULL;
  ITEM *BERinfo = NULL;
  ITEM encodingInfo = {NULL, 0};


  unsigned char *dataToEncrypt = (unsigned char *)"Encrypt this sentence.";
  unsigned int dataToEncryptLen;

  unsigned char *encryptedData = NULL_PTR;
  unsigned int outputLenUpdate, outputLenFinal, outputLenTotal;
  unsigned int encryptedDataLen = 0;

  unsigned char *decryptedData = NULL_PTR;
  unsigned int decryptedDataLen = 0;

  unsigned int algorithmFlag = 0;
  unsigned int keyFlag = 0;


  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 ("RC4 algorithm:  Encryption phase \n");
    RSA_PrintMessage ("================================ \n");

    dataToEncryptLen = T_strlen ((char *)dataToEncrypt) + 1;
    RSA_PrintBuf ("Data To Encrypt", dataToEncrypt, dataToEncryptLen);

    /*  Initialize a random algorithm object using a procedure described in
        samples/common/include/bsfutil.h  */
    if ((status = RSA_CreateRandomAlgorithmObject (&randomAlgorithm)) != 0)
      break;

    /*  Create an algorithm object. */
    if ((status = B_CreateAlgorithmObject (&rc4Encrypter)) != 0)
      break;

    /*  Set the algorithm to a type that does rc4 encryption.
        This sample uses AI_RC4. */
    if ((status = B_SetAlgorithmInfo (rc4Encrypter, AI_RC4,
                                      NULL_PTR)) != 0)
      break;

    /*  Create a key object.  */
    if ((status = B_CreateKeyObject (&rc4Key)) != 0)
      break;

    /*  Set the key object with a random 10-byte key  */
    rc4KeyItem.data = NULL_PTR;
    rc4KeyItem.len = KEY_SIZE;
    rc4KeyItem.data = T_malloc (rc4KeyItem.len);
    if ((status = (rc4KeyItem.data == NULL_PTR)) != 0) {
      status = RSA_DEMO_E_ALLOC;
      break;
    }

    if ((status = B_GenerateRandomBytes
                    (randomAlgorithm, rc4KeyItem.data, rc4KeyItem.len,
                     (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    RSA_PrintBuf ("RC4 Key", rc4KeyItem.data, rc4KeyItem.len);

    if ((status = B_SetKeyInfo (rc4Key, KI_Item, (POINTER)&rc4KeyItem)) != 0)
      break;

    /*  Init */
    if ((status = B_EncryptInit (rc4Encrypter, rc4Key, RC4_CHOOSER,
                                 (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    /*  Update */
    encryptedDataLen = dataToEncryptLen;
    encryptedData = T_malloc (encryptedDataLen);
    if ((status = (encryptedData == NULL_PTR)) != 0) {
      status = RSA_DEMO_E_ALLOC;
      break;
    }

    if ((status = B_EncryptUpdate
                    (rc4Encrypter, encryptedData, &outputLenUpdate,
                     encryptedDataLen, (unsigned char *)dataToEncrypt,
                     dataToEncryptLen, (B_ALGORITHM_OBJ)NULL_PTR,
                     (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    /*  Final */
    if ((status = B_EncryptFinal
                    (rc4Encrypter, encryptedData + outputLenUpdate,
                     &outputLenFinal, encryptedDataLen - outputLenUpdate,
                     (B_ALGORITHM_OBJ)NULL_PTR,
                     (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    outputLenTotal = outputLenUpdate + outputLenFinal;
    encryptedDataLen = outputLenTotal;

    RSA_PrintBuf ("Encrypted Data", encryptedData, encryptedDataLen);


    outputLenTotal = outputLenUpdate = outputLenFinal = 0;

    /* Obtain the algorithm identifier of the encryption algorithm */
    if ((status = B_GetAlgorithmInfo ((POINTER *)&BERinfo, rc4Encrypter,
                                       AI_RC4_BER)) != 0)
      break;

    encodingInfo.len = BERinfo->len;
    encodingInfo.data = (unsigned char *)T_malloc (encodingInfo.len);
    T_memcpy (encodingInfo.data, BERinfo->data, encodingInfo.len);


    /* Print out the algorithm identifier */
    RSA_PrintBuf ("Algorithm Identifier ", BERinfo->data, BERinfo->len);

    /* Obtain the algorithm information from the identifier */
    if ((status = B_DecodeAlgorithmBER (BERinfo->data, BERinfo->len,
                                        &algorithmFlag)) != 0)
      break;

    /* Pring out the algorithm information */
    RSA_PrintBERInfo (algorithmFlag);


    /* Use the algorithm information from B_DecodeAlgorithmBER to set an
       algorithm object and decrypt the encrypted data */

    RSA_PrintMessage ("\nRC4 algorithm:  Decryption phase \n");
    RSA_PrintMessage ("================================ \n");

    /* Create an algorithm object. */
    if ((status = B_CreateAlgorithmObject (&decrypter)) != 0)
      break;

    /* Set the algorithm object.  Use a helper function here defined in
     * alginfoutil.c */
    if (( status = RSA_SetAlgorithmObject (&decrypter, algorithmFlag, &encodingInfo)) != 0)
      break;

    /* Init */
    if ((status = B_DecryptInit (decrypter, rc4Key, RC4_CHOOSER,
                                 (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;


    /* Update */
    decryptedDataLen = dataToEncryptLen;
    decryptedData = T_malloc (encryptedDataLen);
    if ((status = (decryptedData == NULL_PTR)) != 0) {
      status = RSA_DEMO_E_ALLOC;
      break;
    }

    if ((status = B_DecryptUpdate
                    (decrypter, decryptedData, &outputLenUpdate,
                     decryptedDataLen, (unsigned char *)encryptedData,
                     encryptedDataLen, (B_ALGORITHM_OBJ)NULL_PTR,
                     (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    /* Final */
    if ((status = B_DecryptFinal
                    (decrypter, decryptedData + outputLenUpdate, &outputLenFinal,
                     decryptedDataLen - outputLenFinal,
                     (B_ALGORITHM_OBJ)NULL_PTR,
                     (A_SURRENDER_CTX *)NULL_PTR)) != 0)
      break;

    outputLenTotal = outputLenUpdate + outputLenFinal;

    RSA_PrintBuf ("Decrypted Data", decryptedData, outputLenTotal);


    /* Let's create an RSA key pair and run through our decoding algorithm
       to see what it tells us */
    RSA_PrintMessage ("\nRSA Keypair:  Generation \n");
    RSA_PrintMessage ("======================== \n");

    if ((status = RSA_CreateRSAKeypair (&publicKey, &privateKey,
                                        RSA_MODULUS_BITS,
                                        randomAlgorithm)) != 0)
      break;

    if ((status = B_GetKeyInfo ((POINTER *)&cryptocPublicKeyBER, publicKey,
                                KI_RSAPublicBER)) != 0)
      break;

    myPublicKeyBER.len = cryptocPublicKeyBER->len;
    myPublicKeyBER.data = T_malloc (myPublicKeyBER.len);
    if (myPublicKeyBER.data == NULL_PTR) {
      status = RSA_DEMO_E_ALLOC;
      break;
    }

    T_memcpy (myPublicKeyBER.data, cryptocPublicKeyBER->data,
              myPublicKeyBER.len);

    /*  Obtain the key information from the BER encoded key format */
    if ((status = B_DecodeAlgorithmBER (myPublicKeyBER.data,
                                        myPublicKeyBER.len,
                                        &keyFlag)) != 0)
      break;

    RSA_PrintBERInfo (keyFlag);



  } while (0);

  if (status != 0)
    RSA_PrintError ("alginfo sample", status);

  /*  Done with the key and algorithm objects, so destroy them.  */
  B_DestroyKeyObject (&rc4Key);
  B_DestroyKeyObject (&publicKey);
  B_DestroyKeyObject (&privateKey);
  B_DestroyKeyObject (&keyObject);
  B_DestroyAlgorithmObject (&rc4Encrypter);
  B_DestroyAlgorithmObject (&decrypter);
  B_DestroyAlgorithmObject (&randomAlgorithm);

  if (encryptedData != NULL_PTR) {
    T_memset (encryptedData, 0, encryptedDataLen);
    T_free (encryptedData);
    encryptedData = NULL_PTR;
  }

  if (rc4KeyItem.data != NULL_PTR) {
    T_memset (rc4KeyItem.data, 0, rc4KeyItem.len);
    T_free (rc4KeyItem.data);
    rc4KeyItem.data = NULL_PTR;
    rc4KeyItem.len = 0;
  }

  if (myPublicKeyBER.data != NULL_PTR) {
    T_memset (myPublicKeyBER.data, 0, myPublicKeyBER.len);
    T_free (myPublicKeyBER.data);
    myPublicKeyBER.data = NULL_PTR;
    myPublicKeyBER.len = 0;
  }

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

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