Back to index

lightning-sunbird  0.9+nobinonly
Classes | Typedefs | Functions | Variables
certxutl.c File Reference
#include "cert.h"
#include "secitem.h"
#include "secoid.h"
#include "secder.h"
#include "secasn1.h"
#include "certxutl.h"
#include "secerr.h"

Go to the source code of this file.

Classes

struct  _extNode
struct  extRec

Typedefs

typedef struct _extNode extNode

Functions

static CERTCertExtension * GetExtension (CERTCertExtension **extensions, SECItem *oid)
SECStatus cert_FindExtensionByOID (CERTCertExtension **extensions, SECItem *oid, SECItem *value)
SECStatus CERT_GetExtenCriticality (CERTCertExtension **extensions, int tag, PRBool *isCritical)
SECStatus cert_FindExtension (CERTCertExtension **extensions, int tag, SECItem *value)
voidcert_StartExtensions (void *owner, PRArenaPool *ownerArena, void(*setExts)(void *object, CERTCertExtension **exts))
SECStatus CERT_AddExtensionByOID (void *exthandle, SECItem *oid, SECItem *value, PRBool critical, PRBool copyData)
SECStatus CERT_AddExtension (void *exthandle, int idtag, SECItem *value, PRBool critical, PRBool copyData)
SECStatus CERT_EncodeAndAddExtension (void *exthandle, int idtag, void *value, PRBool critical, const SEC_ASN1Template *atemplate)
void PrepareBitStringForEncoding (SECItem *bitsmap, SECItem *value)
SECStatus CERT_EncodeAndAddBitStrExtension (void *exthandle, int idtag, SECItem *value, PRBool critical)
SECStatus CERT_FinishExtensions (void *exthandle)
SECStatus CERT_MergeExtensions (void *exthandle, CERTCertExtension **extensions)
SECStatus CERT_FindBitStringExtension (CERTCertExtension **extensions, int tag, SECItem *retItem)
PRBool cert_HasCriticalExtension (CERTCertExtension **extensions)
PRBool cert_HasUnknownCriticalExten (CERTCertExtension **extensions)

Variables

static unsigned char hextrue = 0xff

Class Documentation

struct _extNode

Definition at line 138 of file certxutl.c.

Collaboration diagram for _extNode:
Class Members
CERTCertExtension * ext
struct _extNode * next

Typedef Documentation

typedef struct _extNode extNode

Function Documentation

SECStatus CERT_AddExtension ( void exthandle,
int  idtag,
SECItem *  value,
PRBool  critical,
PRBool  copyData 
)

Definition at line 248 of file certxutl.c.

{
    SECOidData *oid;
    
    oid = SECOID_FindOIDByTag((SECOidTag)idtag);
    if ( !oid ) {
       return(SECFailure);
    }

    return(CERT_AddExtensionByOID(exthandle, &oid->oid, value, critical, copyData));
}

Here is the call graph for this function:

Here is the caller graph for this function:

SECStatus CERT_AddExtensionByOID ( void exthandle,
SECItem *  oid,
SECItem *  value,
PRBool  critical,
PRBool  copyData 
)

Definition at line 193 of file certxutl.c.

{
    CERTCertExtension *ext;
    SECStatus rv;
    extNode *node;
    extRec *handle;
    
    handle = (extRec *)exthandle;

    /* allocate space for extension and list node */
    ext = (CERTCertExtension*)PORT_ArenaZAlloc(handle->ownerArena,
                                               sizeof(CERTCertExtension));
    if ( !ext ) {
       return(SECFailure);
    }

    node = (extNode*)PORT_ArenaAlloc(handle->arena, sizeof(extNode));
    if ( !node ) {
       return(SECFailure);
    }

    /* add to list */
    node->next = handle->head;
    handle->head = node;
   
    /* point to ext struct */
    node->ext = ext;
    
    /* the object ID of the extension */
    ext->id = *oid;
    
    /* set critical field */
    if ( critical ) {
       ext->critical.data = (unsigned char*)&hextrue;
       ext->critical.len = 1;
    }

    /* set the value */
    if ( copyData ) {
       rv = SECITEM_CopyItem(handle->ownerArena, &ext->value, value);
       if ( rv ) {
           return(SECFailure);
       }
    } else {
       ext->value = *value;
    }
    
    handle->count++;
    
    return(SECSuccess);

}

Here is the call graph for this function:

Here is the caller graph for this function:

SECStatus CERT_EncodeAndAddBitStrExtension ( void exthandle,
int  idtag,
SECItem *  value,
PRBool  critical 
)

Definition at line 301 of file certxutl.c.

{
  SECItem bitsmap;
  
  PrepareBitStringForEncoding (&bitsmap, value);
  return (CERT_EncodeAndAddExtension
         (exthandle, idtag, &bitsmap, critical, SEC_BitStringTemplate));
}

Here is the call graph for this function:

Here is the caller graph for this function:

SECStatus CERT_EncodeAndAddExtension ( void exthandle,
int  idtag,
void value,
PRBool  critical,
const SEC_ASN1Template atemplate 
)

Definition at line 262 of file certxutl.c.

{
    extRec *handle;
    SECItem *encitem;

    handle = (extRec *)exthandle;

    encitem = SEC_ASN1EncodeItem(handle->ownerArena, NULL, value, atemplate);
    if ( encitem == NULL ) {
       return(SECFailure);
    }

    return CERT_AddExtension(exthandle, idtag, encitem, critical, PR_FALSE);
}

Here is the call graph for this function:

Here is the caller graph for this function:

SECStatus CERT_FindBitStringExtension ( CERTCertExtension **  extensions,
int  tag,
SECItem *  retItem 
)

Definition at line 426 of file certxutl.c.

{
    SECItem wrapperItem, tmpItem = {siBuffer,0};
    SECStatus rv;
    PRArenaPool *arena = NULL;
    
    wrapperItem.data = NULL;
    tmpItem.data = NULL;
    
    arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE);
    
    if ( ! arena ) {
       return(SECFailure);
    }
    
    rv = cert_FindExtension(extensions, tag, &wrapperItem);
    if ( rv != SECSuccess ) {
       goto loser;
    }

    rv = SEC_QuickDERDecodeItem(arena, &tmpItem, SEC_BitStringTemplate, 
                         &wrapperItem);

    if ( rv != SECSuccess ) {
       goto loser;
    }

    retItem->data = (unsigned char *)PORT_Alloc( ( tmpItem.len + 7 ) >> 3 );
    if ( retItem->data == NULL ) {
       goto loser;
    }
    
    PORT_Memcpy(retItem->data, tmpItem.data, ( tmpItem.len + 7 ) >> 3);
    retItem->len = tmpItem.len;
    
    rv = SECSuccess;
    goto done;
    
loser:
    rv = SECFailure;

done:
    if ( arena ) {
       PORT_FreeArena(arena, PR_FALSE);
    }
    
    if ( wrapperItem.data ) {
       PORT_Free(wrapperItem.data);
    }

    return(rv);
}

Here is the call graph for this function:

SECStatus cert_FindExtension ( CERTCertExtension **  extensions,
int  tag,
SECItem *  value 
)

Definition at line 125 of file certxutl.c.

{
    SECOidData *oid;
    
    oid = SECOID_FindOIDByTag((SECOidTag)tag);
    if ( !oid ) {
       return(SECFailure);
    }

    return(cert_FindExtensionByOID(extensions, &oid->oid, value));
}

Here is the call graph for this function:

SECStatus cert_FindExtensionByOID ( CERTCertExtension **  extensions,
SECItem *  oid,
SECItem *  value 
)

Definition at line 79 of file certxutl.c.

{
    CERTCertExtension *ext;
    SECStatus rv = SECSuccess;
    
    ext = GetExtension (extensions, oid);
    if (ext == NULL) {
       PORT_SetError (SEC_ERROR_EXTENSION_NOT_FOUND);
       return (SECFailure);
    }
    if (value)
       rv = SECITEM_CopyItem(NULL, value, &ext->value);
    return (rv);
}

Here is the call graph for this function:

Definition at line 312 of file certxutl.c.

{
    extRec *handle;
    extNode *node;
    CERTCertExtension **exts;
    SECStatus rv = SECFailure;
    
    handle = (extRec *)exthandle;

    /* allocate space for extensions array */
    exts = PORT_ArenaNewArray(handle->ownerArena, CERTCertExtension *,
                           handle->count + 1);
    if (exts == NULL) {
       goto loser;
    }

    /* put extensions in owner object and update its version number */

#ifdef OLD
    switch (handle->type) {
      case CertificateExtensions:
       handle->owner.cert->extensions = exts;
       DER_SetUInteger (ownerArena, &(handle->owner.cert->version),
                      SEC_CERTIFICATE_VERSION_3);
       break;
      case CrlExtensions:
       handle->owner.crl->extensions = exts;
       DER_SetUInteger (ownerArena, &(handle->owner.crl->version),
                      SEC_CRL_VERSION_2);
       break;
      case OCSPRequestExtensions:
       handle->owner.request->tbsRequest->requestExtensions = exts;
       break;
      case OCSPSingleRequestExtensions:
       handle->owner.singleRequest->singleRequestExtensions = exts;   
       break;
      case OCSPResponseSingleExtensions:
       handle->owner.singleResponse->singleExtensions = exts;  
       break;
    }
#endif

    handle->setExts(handle->object, exts);
       
    /* update the version number */

    /* copy each extension pointer */
    node = handle->head;
    while ( node ) {
       *exts = node->ext;
       
       node = node->next;
       exts++;
    }

    /* terminate the array of extensions */
    *exts = 0;

    rv = SECSuccess;

loser:
    /* free working arena */
    PORT_FreeArena(handle->arena, PR_FALSE);
    return rv;
}

Here is the call graph for this function:

Here is the caller graph for this function:

SECStatus CERT_GetExtenCriticality ( CERTCertExtension **  extensions,
int  tag,
PRBool isCritical 
)

Definition at line 96 of file certxutl.c.

{
    CERTCertExtension *ext;
    SECOidData *oid;

    if (!isCritical)
       return (SECSuccess);
    
    /* find the extension in the extensions list */
    oid = SECOID_FindOIDByTag((SECOidTag)tag);
    if ( !oid ) {
       return(SECFailure);
    }
    ext = GetExtension (extensions, &oid->oid);
    if (ext == NULL) {
       PORT_SetError (SEC_ERROR_EXTENSION_NOT_FOUND);
       return (SECFailure);
    }

    /* If the criticality is omitted, then it is false by default.
       ex->critical.data is NULL */
    if (ext->critical.data == NULL)
       *isCritical = PR_FALSE;
    else
       *isCritical = (ext->critical.data[0] == 0xff) ? PR_TRUE : PR_FALSE;
    return (SECSuccess);    
}

Here is the call graph for this function:

PRBool cert_HasCriticalExtension ( CERTCertExtension **  extensions)

Definition at line 481 of file certxutl.c.

{
    CERTCertExtension **exts;
    CERTCertExtension *ext = NULL;
    PRBool hasCriticalExten = PR_FALSE;
    
    exts = extensions;
    
    if (exts) {
       while ( *exts ) {
           ext = *exts;
           /* If the criticality is omitted, it's non-critical */
           if (ext->critical.data && ext->critical.data[0] == 0xff) {
              hasCriticalExten = PR_TRUE;
              break;
           }
           exts++;
       }
    }
    return (hasCriticalExten);
}
PRBool cert_HasUnknownCriticalExten ( CERTCertExtension **  extensions)

Definition at line 504 of file certxutl.c.

{
    CERTCertExtension **exts;
    CERTCertExtension *ext = NULL;
    PRBool hasUnknownCriticalExten = PR_FALSE;
    
    exts = extensions;
    
    if (exts) {
       while ( *exts ) {
           ext = *exts;
           /* If the criticality is omitted, it's non-critical.
              If an extension is critical, make sure that we know
              how to process the extension.
             */
           if (ext->critical.data && ext->critical.data[0] == 0xff) {
              if (SECOID_KnownCertExtenOID (&ext->id) == PR_FALSE) {
                  hasUnknownCriticalExten = PR_TRUE;
                  break;
              }
           }
           exts++;
       }
    }
    return (hasUnknownCriticalExten);
}

Here is the call graph for this function:

SECStatus CERT_MergeExtensions ( void exthandle,
CERTCertExtension **  extensions 
)

Definition at line 379 of file certxutl.c.

{
    CERTCertExtension *ext;
    SECStatus rv = SECSuccess;
    SECOidTag tag;
    extNode *node;
    extRec *handle = exthandle;
    
    if (!exthandle || !extensions) {
       PORT_SetError(SEC_ERROR_INVALID_ARGS);
        return SECFailure;
    }
    while ((ext = *extensions++) != NULL) {
        tag = SECOID_FindOIDTag(&ext->id);
        for (node=handle->head; node != NULL; node=node->next) {
            if (tag == 0) {
                if (SECITEM_ItemsAreEqual(&ext->id, &node->ext->id))
                    break;
            }
            else {
                if (SECOID_FindOIDTag(&node->ext->id) == tag) {
                    break;
                }
            }
        }
        if (node == NULL) {
            PRBool critical = (ext->critical.len != 0 &&
                            ext->critical.data[ext->critical.len - 1] != 0);
            if (critical && tag == SEC_OID_UNKNOWN) {
               PORT_SetError(SEC_ERROR_UNKNOWN_CRITICAL_EXTENSION);
               rv = SECFailure;
               break;
            }
            /* add to list */
            rv = CERT_AddExtensionByOID (exthandle, &ext->id, &ext->value,
                                         critical, PR_TRUE);
            if (rv != SECSuccess)
                break;
        }
    }
    return rv;
}

Here is the call graph for this function:

Here is the caller graph for this function:

void* cert_StartExtensions ( void owner,
PRArenaPool ownerArena,
void(*)(void *object, CERTCertExtension **exts)  setExts 
)

Definition at line 159 of file certxutl.c.

{
    PRArenaPool *arena;
    extRec *handle;

    arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE);
    if ( !arena ) {
       return(0);
    }

    handle = (extRec *)PORT_ArenaAlloc(arena, sizeof(extRec));
    if ( !handle ) {
       PORT_FreeArena(arena, PR_FALSE);
       return(0);
    }

    handle->object = owner;
    handle->ownerArena = ownerArena;
    handle->setExts = setExts;

    handle->arena = arena;
    handle->head = 0;
    handle->count = 0;
    
    return(handle);
}

Here is the call graph for this function:

static CERTCertExtension* GetExtension ( CERTCertExtension **  extensions,
SECItem *  oid 
) [static]

Definition at line 56 of file certxutl.c.

{
    CERTCertExtension **exts;
    CERTCertExtension *ext = NULL;
    SECComparison comp;

    exts = extensions;
    
    if (exts) {
       while ( *exts ) {
           ext = *exts;
           comp = SECITEM_CompareItem(oid, &ext->id);
           if ( comp == SECEqual ) 
              break;

           exts++;
       }
       return (*exts ? ext : NULL);
    }
    return (NULL);
}

Here is the call graph for this function:

Here is the caller graph for this function:

void PrepareBitStringForEncoding ( SECItem *  bitsmap,
SECItem *  value 
)

Definition at line 279 of file certxutl.c.

{
  unsigned char onebyte;
  unsigned int i, len = 0;

  /* to prevent warning on some platform at compile time */ 
  onebyte = '\0';   
  /* Get the position of the right-most turn-on bit */ 
  for (i = 0; i < (value->len ) * 8; ++i) {
      if (i % 8 == 0)
         onebyte = value->data[i/8];
      if (onebyte & 0x80)
         len = i;            
      onebyte <<= 1;
      
  }
  bitsmap->data = value->data;
  /* Add one here since we work with base 1 */ 
  bitsmap->len = len + 1;
}

Variable Documentation

unsigned char hextrue = 0xff [static]

Definition at line 187 of file certxutl.c.