RSA BSAFE Cert-C

Certificate Components for C

Crypto-C 6.2.1 Developer's Guide
Search

nameutil.c

Prints information contained in a name object in a readable manner. Gathers user input to place into a Name object.

/* $Id: nameutil.c,v 1.7 2004/03/02 05:18:38 gsingh Exp $ */
/* nameutil.c
** Copyright (c) 1999-2003, RSA Security Inc.
**
** This file is used to demonstrate how to interface to an RSA Security
** licensed development product.  You have a royalty-free right to use,
** modify, reproduce and distribute this demonstration file (including
** any modified version), provided that you agree that RSA Security has
** no warranty, implied or otherwise, or liability for this demonstration
** file or any modified version.
**
** This file contains routines that are used to print the information
** contained in a name object in a readable manner, as well as routines used
** to gather user input to place into a name object.
*/

#include "nameutil.h"

#ifdef _MSC_VER
# pragma warning (disable: 171) /* invalid type conversion (often of very similar ptrs) */
#endif

RSA_DEMO_TABLE_ENTRY RSA_DEMO_AT_TABLE[RSA_DEMO_AT_COUNT];

unsigned char AT_TELEPHONE_NUMBER[AT_TELEPHONE_NUMBER_LEN] = {
  0x55, 0x04, 0x14  /* OID from X.520 */
};

unsigned char AT_UID[AT_UID_LEN] = {
  0x09, 0x92, 0x26, 0x89, 0x93, 0xF2, 0x2C, 0x64,
  0x01, 0x01
};

void InitAtTable () {
  static int flag = 0;

  if (flag)
    return;
  flag = 1;

  RSA_DEMO_AT_TABLE[0].description = "Serial Number";
  RSA_DEMO_AT_TABLE[0].val.at.data = AT_SERIAL_NUMBER;
  RSA_DEMO_AT_TABLE[0].val.at.len = AT_SERIAL_NUMBER_LEN;
  RSA_DEMO_AT_TABLE[1].description = "Country";
  RSA_DEMO_AT_TABLE[1].val.at.data = AT_COUNTRY;
  RSA_DEMO_AT_TABLE[1].val.at.len = AT_COUNTRY_LEN;  
  RSA_DEMO_AT_TABLE[2].description = "State";
  RSA_DEMO_AT_TABLE[2].val.at.data = AT_STATE;
  RSA_DEMO_AT_TABLE[2].val.at.len = AT_STATE_LEN;  
  RSA_DEMO_AT_TABLE[3].description = "Locality";
  RSA_DEMO_AT_TABLE[3].val.at.data = AT_LOCALITY;
  RSA_DEMO_AT_TABLE[3].val.at.len = AT_LOCALITY_LEN;  
  RSA_DEMO_AT_TABLE[4].description = "Organization";
  RSA_DEMO_AT_TABLE[4].val.at.data = AT_ORGANIZATION;
  RSA_DEMO_AT_TABLE[4].val.at.len = AT_ORGANIZATION_LEN;  
  RSA_DEMO_AT_TABLE[5].description = "Organizational Unit";
  RSA_DEMO_AT_TABLE[5].val.at.data = AT_ORG_UNIT;
  RSA_DEMO_AT_TABLE[5].val.at.len = AT_ORG_UNIT_LEN;  
  RSA_DEMO_AT_TABLE[6].description = "Common Name";
  RSA_DEMO_AT_TABLE[6].val.at.data = AT_COMMON_NAME;
  RSA_DEMO_AT_TABLE[6].val.at.len = AT_COMMON_NAME_LEN;  
  RSA_DEMO_AT_TABLE[7].description = "Title";
  RSA_DEMO_AT_TABLE[7].val.at.data = AT_TITLE;
  RSA_DEMO_AT_TABLE[7].val.at.len = AT_TITLE_LEN;  
  RSA_DEMO_AT_TABLE[8].description = "Street Address";
  RSA_DEMO_AT_TABLE[8].val.at.data = AT_STREET_ADDRESS;
  RSA_DEMO_AT_TABLE[8].val.at.len = AT_STREET_ADDRESS_LEN;  
  RSA_DEMO_AT_TABLE[9].description = "Postal Code";
  RSA_DEMO_AT_TABLE[9].val.at.data = AT_POSTAL_CODE;
  RSA_DEMO_AT_TABLE[9].val.at.len = AT_POSTAL_CODE_LEN;  
  RSA_DEMO_AT_TABLE[10].description = "Email Address";
  RSA_DEMO_AT_TABLE[10].val.at.data = AT_EMAIL_ADDRESS;
  RSA_DEMO_AT_TABLE[10].val.at.len = AT_EMAIL_ADDRESS_LEN;
  RSA_DEMO_AT_TABLE[11].description = "Telephone Number";
  RSA_DEMO_AT_TABLE[11].val.at.data = AT_TELEPHONE_NUMBER;
  RSA_DEMO_AT_TABLE[11].val.at.len = AT_TELEPHONE_NUMBER_LEN;
  RSA_DEMO_AT_TABLE[12].description = "UID";
  RSA_DEMO_AT_TABLE[12].val.at.data = AT_UID;
  RSA_DEMO_AT_TABLE[12].val.at.len = AT_UID_LEN;
  /*  If you want to add more entries here, be sure to update the definition of
   *  RSA_DEMO_AT_COUNT in nameutil.h!
   */
}  /* end InitAtTable */

int RSA_AttribTypePrompt (unsigned char **attribType,
                          unsigned int *attribTypeLen)
{
  int status = 0;
  RSA_DEMO_TABLE_ENTRY *tableEntry = (RSA_DEMO_TABLE_ENTRY *)0;

  InitAtTable ();

  RSA_PrintMessage ("Attribute Type Choices\n");
  status = ChooseTableEntryPrompt (RSA_DEMO_AT_TABLE, RSA_DEMO_AT_COUNT,
                                   &tableEntry);
  if (status != 0) {
    *attribType = NULL_PTR;
    *attribTypeLen = 0;
    goto CLEANUP;
  }

  *attribType = tableEntry->val.at.data;
  *attribTypeLen = tableEntry->val.at.len;

CLEANUP:
  if (status != 0)
    RSA_PrintError ("RSA_AttribTypePrompt", status);

  return status;
}  /* end RSA_AttribTypePrompt */

int RSA_GetAttribTypeDesc (unsigned char *attribType,
                           unsigned int attribTypeLen, char **desc)
{
  int status = 0, i = 0;

  InitAtTable ();
  *desc = (char *)0;

  for (i = 0; i < RSA_DEMO_AT_COUNT; i++)
    if (attribTypeLen == RSA_DEMO_AT_TABLE[i].val.at.len &&
        T_memcmp (attribType, RSA_DEMO_AT_TABLE[i].val.at.data,
                  RSA_DEMO_AT_TABLE[i].val.at.len) == 0) {
      *desc = RSA_DEMO_AT_TABLE[i].description;
      break;
    }

  if (*desc == (char *)0)
    status = RSA_DEMO_E_NOT_FOUND;

  return status;
}  /* end RSA_GetAttribTypeDesc */

int RSA_PrintNameObject (char *label, NAME_OBJ nameObj)
{
  int status = 0;
  int valueTag = 0, newLevel = 0;
  unsigned char *type = NULL_PTR, *value = NULL_PTR;
  unsigned int typeLen = 0, valueLen = 0;
  unsigned int avaCount = 0, index = 0;

  char *attribString = (char *)0, *valueTagString = (char *)0;

  if (label != (char *)0)
    RSA_PrintMessage ("%s\n", label);

  status = C_GetNameAVACount (nameObj, &avaCount);
  if (status != 0)
    goto CLEANUP;

  for (index = 0; index < avaCount; index++) {
    status = C_GetNameAVA (nameObj, index, &type, &typeLen, &valueTag, &value,
                           &valueLen, &newLevel);
    if (status != 0)
      goto CLEANUP;

    if (newLevel == 1)
      RSA_PrintMessage ("********************\n");

    status = RSA_GetAttribTypeDesc (type, typeLen, &attribString);
    if (status == RSA_DEMO_E_NOT_FOUND) {
      RSA_PrintBuf ("Unrecognized Attribute Type", type, typeLen);
      status = 0;
    }
    else if (status != 0)
      goto CLEANUP;

    status = RSA_GetValueTagDesc (valueTag, &valueTagString);
    if (status == RSA_DEMO_E_NOT_FOUND) {
      RSA_PrintMessage ("Unrecognized Attribute Value Tag = %i\n", valueTag);
      status = 0;
    }
    else if (status != 0)
      goto CLEANUP;

    if (attribString != (char *)0 && valueTagString != (char *)0) {
      RSA_PrintMessage ("%s, %s (%u bytes):\n", attribString, valueTagString,
                        valueLen);
      RSA_PrintBuf((char *)0, value, valueLen);
    }
    else if (attribString == (char *)0 && valueTagString == (char *)0)
      RSA_PrintBuf ("Attribute Value", value, valueLen);
    else if (attribString == (char *)0)
      RSA_PrintBuf (valueTagString, value, valueLen);
    else
      RSA_PrintBuf (attribString, value, valueLen);
  }

CLEANUP:
  if (status != 0)
    RSA_PrintError ("RSA_PrintNameObjInfo", status);

  return status;
}  /* end RSA_PrintNameObjInfo */

int RSA_GetInputToNameObject (NAME_OBJ nameObj)
{
  int status = 0;

  unsigned char *attributeType = NULL_PTR;
  unsigned int attributeTypeLen = 0;
  int valueTag = 0;
  char valueString[RSA_DEMO_MAX_LINE_LEN];

  /*  Keep going until user enters a blank (just hits return in response to the
   *  prompt).
   */
  for (;;) {
    /*  Prompt user for attribute type  */
    status = RSA_AttribTypePrompt (&attributeType, &attributeTypeLen);
    if (status == RSA_DEMO_E_CANCEL) {
      status = 0;
      break;
    }
    else if (status != 0)
      goto CLEANUP;
    
    /*  Prompt user for type value tag  */
    status = RSA_ValueTagPrompt (&valueTag);
    if (status == RSA_DEMO_E_CANCEL) {
      status = 0;
      break;
    }
    else if (status != 0)
      goto CLEANUP;
    
    /*  Prompt user for type value string  */
    status = RSA_GetCommand (valueString, sizeof (valueString),
                             "Enter attribute value string");
    if (status != 0)
      goto CLEANUP;    

    if (T_strlen (valueString) == 0)
      break;
    
    /*  Add AVA to name object.  For now we assume distinct levels for each
     *  new AVA.  An exercise would be to modify this to prompt the user for
     *  whether or not the new AVA begins a new level.
     */
    status = C_AddNameAVA (nameObj, attributeType, attributeTypeLen, valueTag,
                           (unsigned char *)valueString,
                           T_strlen (valueString), 1,
                           (unsigned int *)0);
    if (status != 0) {
      RSA_PrintError ("adding attribute to name object", status);
      if (status == E_ATTRIBUTE_TAG)
        RSA_PrintError ("The string value tag you selected is not compatible \
with the attribute\ntype.  Refer to the LRM for the compatible types.", 0);
      RSA_PrintMessage ("Try again.\n");
    }
  }
  
CLEANUP:
  if (status != 0)
    RSA_PrintError ("RSA_GetInputToNameObject", status);

  return status;
}  /* end RSA_GetInputToNameObject */

int RSA_GetNameObject (NAME_OBJ nameObj, char *label)
{
  int status = 0;
  unsigned char *nameDer = NULL_PTR;
  unsigned int nameDerLen = 0;

  if (label != (char *)0)
    RSA_PrintMessage ("Enter name of file containing %s name object binary\n",
                      label);
  
  status = RSA_GetFileToAllocBuffer (&nameDer, &nameDerLen,
                                     "(blank to create a new one)");
  if (status == RSA_DEMO_E_CANCEL) {
    status = RSA_GetInputToNameObject (nameObj);
    /* whatever happens, we're done here */
    goto CLEANUP;
  }
  if (status != 0)
    goto CLEANUP;

  status = C_SetNameBER (nameObj, nameDer, nameDerLen);
  if (status != 0)
    goto CLEANUP;
  
CLEANUP:
  if (status != 0)
    RSA_PrintError ("RSA_GetNameObject", status);

  T_free (nameDer);
  
  return status;
}  /* end RSA_GetNameObject */

int RSA_CopyNameObject (NAME_OBJ *newName, NAME_OBJ source)
{
  int status;
  ITEM nameBer = {NULL_PTR, 0};

  status = C_CreateNameObject (newName);
  if (status != 0)
    goto CLEANUP;
  
  status = C_GetNameDER (source, &nameBer.data, &nameBer.len);
  if (status != 0)
    goto CLEANUP;
  
  status = C_SetNameBER (*newName, nameBer.data, nameBer.len);
  if (status != 0)
    goto CLEANUP;

CLEANUP:
  if (status != 0) {
    C_DestroyNameObject (newName);
    RSA_PrintError ("RSA_CopyNameObject", status);
  }

  return status;
}  /* end RSA_CopyNameObject */

Copyright (c) 1999-2005 RSA Security Inc. All rights reserved. 067-001001-2720-001-000 - 2.7.2