📄 pgpx509cert_util.c
字号:
/*******************************************************************
*
* This file was generated by TIS/ASN1COMP Ver. 4.2, an ASN.1 compiler.
* TIS/ASN1COMP is Copyright (c) 1998, TIS Labs at Network Associates, Inc.
*
* This file was AUTOMATICALLY GENERATED on Tue May 18 17:09:44 1999
*
******************************************************************/
/**********************************************************************
* pgpX509Cert_util.c
*
* Utility routines for ASN.1 coding
************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include "pgpX509Cert_util.h"
#ifdef PGPASN_TRACE
int PGPASN_TRACE_LEVEL = 0;
#endif
/***********************************************************************
* PGPASN_ErrorHalt
*
* a dummy routine, called if error, on which one can halt/
*************************************************************************/
void PGPASN_ErrorHalt(int x)
{
(void)x; /* not usted */
return;
} /* err_halt */
/**********************************************************************
* Default mem. mgmt callbacks
*
* These are defaults that the user can use if desired, or use them
* as models for your own set of memory mgmt. callbacks.
***********************************************************************/
/* default memory allocator */
static void *
PGPASN_DefaultMemoryAllocationProc(
PGPASN_MemoryMgr *mgr,
size_t requestSize)
{
(void)mgr;
return ( malloc(requestSize) );
} /* PGPASN_DefaultMemoryAllocationProc */
/* default memory reallocator */
static int
PGPASN_DefaultMemoryReallocationProc(
PGPASN_MemoryMgr *mgr,
void **allocation,
size_t newAllocationSize)
{
int err;
void *newPtr = NULL;
void *oldPtr = *allocation;
(void)mgr;
newPtr = realloc(oldPtr, newAllocationSize);
if (newPtr == NULL) {
err = kPGPASNError_ErrOutOfMemory;
}
else {
err = 0;
*allocation = newPtr;
}
return err;
} /* PGPASN_MemoryMgrReallocationProc */
/* default memory deallocation routine */
static int
PGPASN_DefaultMemoryDeallocationProc(
PGPASN_MemoryMgr *mgr,
void *allocation)
{
(void)mgr;
free(allocation);
return 0;
} /* PGPASN_MemoryMgrDeallocationProc */
/* the default PGPASN_MemoryMgr structure for the user */
PGPASN_MemoryMgr PGPASN_defaultMemoryMgrStruct = {
NULL,
PGPASN_DefaultMemoryAllocationProc,
PGPASN_DefaultMemoryReallocationProc,
PGPASN_DefaultMemoryDeallocationProc
};
/***************************************************************************
* PGPASN_CompareElems
* A routine to provide to the qsort routine for comparing two
* <prefix>PrimVariableBlock blocks. This is used by the pack
* routines for SET OF structures. This assumes the compare should
* use the length of the longer element provided and for SET OF, then* provided elements should have 0's at the ends of shorter elements.
****************************************************************************/
int PGPASN_CompareElems(const void *a, const void *b)
{
int length;
PGPASN_VariableBlock *locala = (PGPASN_VariableBlock *)a;
PGPASN_VariableBlock *localb = (PGPASN_VariableBlock *)b;
if (locala->len > localb->len)
length = locala->len;
else
length = localb->len;
return(memcmp(locala->val, localb->val, length));
} /* PGPASN_CompareElems */
/************************************************************************
* PGPASN_LengthSize -- for scanning the length of a basic integer
* for the ASN.1 length field after the tag.
*************************************************************************/
size_t PGPASN_LengthSize(size_t x)
{
if ( x <= 127 ) return 1;
else if ( x < 0x100 ) return 2;
else if ( x < 0x10000 ) return 3;
else if ( x < 0x1000000 ) return 4;
else return 5;
} /* LengthSize */
/************************************************************************
* Tagged -- compute and return the size of a tagged ASN.1 object
* whose size without the tag would be (inner).
*************************************************************************/
size_t PGPASN_Tagged(size_t inner, int seqlike )
{
if ( inner == 0 && ! seqlike )
return (0);
return ( 1 + inner + PGPASN_LengthSize(inner) );
} /* Tagged */
/************************************************************************
* PGPASN_PutByte -- put an ASN.1 type byte to op
*************************************************************************/
size_t PGPASN_PutByte( unsigned char *buf, unsigned char byte )
{
*buf = byte;
return 1;
} /* PGPASN_PutByte */
/************************************************************************
* PGPASN_PutLength -- put a length field to opp
************************************************************************/
size_t PGPASN_PutLength( unsigned char *buf, size_t length )
{
unsigned char *bufptr = buf;
size_t size = PGPASN_LengthSize(length) - 1;
unsigned char bytes[4] ;
unsigned char *bp = &(bytes[3]) ; /* pointer for unpacking */
switch (size) {
case 4: *(bp--) = (unsigned char)length & 0xff ; length >>= 8 ;
case 3: *(bp--) = (unsigned char)length & 0xff ; length >>= 8 ;
case 2: *(bp--) = (unsigned char)length & 0xff ; length >>= 8 ;
case 1: *(bp--) = (unsigned char)length & 0xff ; length >>= 8 ;
default: /* fall through */ ;
} /* turn x into bytes */
/* only need one byte for length */
if (size == 0)
*(bufptr++) = (unsigned char)(length & 0x7f);
/* otherwise first byte is number of bytes needed for size */
else
*(bufptr++) = (unsigned char)(0x80 | size) ;
size = 4 - size; /* as an index into bytes[] */
while (size < 4) *(bufptr++) = bytes[size++] ;
/* return the number of bytes used */
return (size_t)(bufptr-buf);
} /* PGPASN_PutLength */
/************************************************************************
* PGPASN_GetByte -- get an ASN.1 type byte to op
*************************************************************************/
size_t PGPASN_GetByte(const unsigned char *buf, unsigned char *byte)
{
*byte = *buf;
return 1;
} /* PGPASN_GetByte */
/************************************************************************
* PGPASN_GetLength -- fetch a length field from opp and return it
* If this is indefinite length, then return -1 for the length.
*************************************************************************/
size_t PGPASN_GetLength(const unsigned char *buf, size_t *length)
{
size_t bytesused;
unsigned long x ;
unsigned char c ;
c = *buf; /* get the control byte (or length) */
bytesused = 1;
if (c == 0x80) { /* this is indefinite length */
*length = -1;
return bytesused;
}
if ((c & 0x80) == 0) { /* have the length already */
*length = (size_t)c; /* note the byte we used */
PGPASN_TRACE_PRINT_LENGTH(c);
return bytesused; /* return the length */
} /* if */
c &= 0x7f ; /* get the number of bytes of length */
x = 0 ; /* clear x */
while ((c--) > 0) {
x <<= 8 ; /* shift up the word */
x |= (unsigned long)*(buf + bytesused); /* gather the next byte */
bytesused++;
} /* pack as integer */
PGPASN_TRACE_PRINT_LENGTH((int)x);
*length = (size_t)x; /* note the bytes used */
return bytesused; /* return the length */
} /* PGPASN_GetLength */
/************************************************************************
* PGPASN_PutTag
*
* Put a tag field (tag + length) to the output block
*************************************************************************/
size_t PGPASN_PutTag( unsigned char *buf, unsigned char tagbyte, size_t length )
{
size_t bytesused;
bytesused = PGPASN_PutByte(buf, tagbyte);
bytesused += PGPASN_PutLength(buf+bytesused, length);
return bytesused;
} /* PGPASN_PutTag */
/************************************************************************
* PGPASN_TakeTag
*
* Get a tag field from the input block and return its length
*************************************************************************/
size_t PGPASN_TakeTag(const unsigned char *buf, unsigned char tag, size_t *length)
{
size_t bytesused = 0;
*length = 0;
if (buf == NULL) return 0;
if (*buf != tag) return 0;
/* have that tag */
bytesused = 1; /* consume the tag byte */
bytesused += PGPASN_GetLength(buf+bytesused, length);
return bytesused;
} /* PGPASN_TakeTag */
/************************************************************************
* Basic variable block routines
*************************************************************************/
void *pgpasn_NewVariableBlock(PGPASN_CONTEXT *ctx)
{
PGPASN_VariableBlock *block = NULL ;
if (ctx == NULL)
return NULL;
block = (PGPASN_VariableBlock *) PGPASN_Alloc(ctx->memMgr,
sizeof(PGPASN_VariableBlock) );
if (block != NULL)
memset(block, 0, sizeof(PGPASN_VariableBlock)) ;
return (void *)block;
} /* pgpasn_NewVariableBlock */
size_t pgpasn_SizeofVariableBlock(PGPASN_CONTEXT *ctx,
PGPASN_VariableBlock *block,
int outerSizeFlag)
{
(void)ctx; /* for future use */
return pgpasn_SizeofVariableBlockInternal(block, outerSizeFlag, PGPASN_FALSE);
}
/*****
*
* internal pgpasn_SizeofVariableBlock
*
* This internal routine handles the case where there is an
* explicitly tagged field in a constructed ASN block. The final length
* returned will be increased by the explicit tag bits (using the tagged()
* routine) only if the previous calculations don't result in zero.
*
* It is assumed that outerSizeFlag will not be FALSE when expTaggedSize
* is TRUE. This is handled by the generated code. It does not call
* _sizeof with this case. Also, the wrapper routine above calls this
* routine with expTaggedSize as FALSE. So, this routine doesn't do any
* error checking in that respect.
*
*****/
size_t pgpasn_SizeofVariableBlockInternal(
PGPASN_VariableBlock *block,
int outerSizeFlag,
int expTaggedSize)
{
size_t length;
if (block == NULL)
return (0);
length = (size_t)block->len;
if (outerSizeFlag == PGPASN_TRUE)
length = length + 1 + PGPASN_LengthSize(block->len);
if (expTaggedSize == PGPASN_TRUE)
length = PGPASN_Tagged(length, 0);
return length;
} /* pgpasn_SizeofVariableBlockInternal */
void pgpasn_DropInPlaceVariableBlock(PGPASN_CONTEXT *ctx,
PGPASN_VariableBlock *f )
{
if (ctx == NULL)
return;
if (f != NULL && f->val != NULL) {
PGPASN_Free(ctx->memMgr, f->val);
f->val = NULL;
}
} /* pgpasn_DropInPlaceVariableBlock */
void pgpasn_FreeVariableBlock(PGPASN_CONTEXT *ctx,
PGPASN_VariableBlock *f)
{
if (ctx == NULL)
return;
pgpasn_DropInPlaceVariableBlock(ctx, f);
if (f != NULL)
PGPASN_Free(ctx->memMgr, f);
return;
} /* pgpasn_FreeVariableBlock */
/************************************************************************
* pack and unpack -- taking block type as a parameter/
*************************************************************************/
static size_t UnpkInPlaceSegments(
PGPASN_CONTEXT *ctx,
int indefFlag, /* is this an indefinite length block or not? */
unsigned char exptag, /* my expected block tag */
PGPASN_VariableBlock *asnblock, /* output block */
const unsigned char *buf, /* loc of input pointer */
size_t buflen, /* max end of my region */
int *erret) /* error return location */
{
size_t bytesused = 0;
size_t datasize;
/* validity of ctx and erret checked in UnpkInPlaceVariableBlock */
if (buf == NULL) {
PGPASN_ERR(kPGPASNError_ErrUnpackNoBlockPtr);
return 0;
}
/* validity of asnblock checked in UnpkInPlaceVariableBlock */
asnblock->val = NULL;
asnblock->len = 0;
/* while there are segments */
while (1) {
/* For indef length end-of-contents is 0x00 0x00 and we
have to eat those two bytes, otherwise we see if we've
used up all the available data yet */
if ( indefFlag == 1 &&
(*(buf+bytesused) == 0x00 && *(buf+bytesused+1) == 0x00) ) {
bytesused += 2;
break;
}
else if (indefFlag == 0 && bytesused == buflen)
break;
if (*buf != exptag) {
PGPASN_ERR(kPGPASNError_ErrUnpackInvalidEncoding);
return 0;
}
bytesused++; /* skip the tag byte */
datasize = 0;
bytesused += PGPASN_GetLength(buf+bytesused, &datasize);
/* no nested indef lengths for string types */
if ((int)datasize == -1) {
PGPASN_ERR(kPGPASNError_ErrUnpackInvalidEncoding);
return 0;
}
if (bytesused + datasize > buflen) {
PGPASN_ERR(kPGPASNError_ErrUnpackOverrun); /* note this error */
return 0;
}
if (datasize == 0)
continue;
PGPASN_Realloc(ctx->memMgr,
(void **)&asnblock->val, asnblock->len+datasize);
if (asnblock->val == NULL) {
PGPASN_ERR(kPGPASNError_ErrOutOfMemory);
return 0;
}
memcpy(asnblock->val + asnblock->len,
buf+bytesused, datasize);
asnblock->len += datasize;
bytesused += datasize;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -