📄 certval.c
字号:
assert( isWritePtr( errorLocus, sizeof( CRYPT_ATTRIBUTE_TYPE ) ) );
assert( isWritePtr( errorType, sizeof( CRYPT_ERRTYPE_TYPE ) ) );
/* Clear return value */
*errorEntry = NULL;
/* If the validity list is empty there's nothing to do */
if( listPtr == NULL )
return( CRYPT_OK );
/* Check the attributes for each entry in a validation list */
for( validityEntry = listPtr, iterationCount = 0;
validityEntry != NULL && iterationCount < FAILSAFE_ITERATIONS_LARGE;
validityEntry = validityEntry->next, iterationCount++ )
{
int status;
/* If there's nothing to check, skip this entry */
if( validityEntry->attributes == NULL )
continue;
status = checkAttributes( ATTRIBUTE_CERTIFICATE,
validityEntry->attributes,
errorLocus, errorType );
if( cryptStatusError( status ) )
{
/* Remember the entry that caused the problem */
*errorEntry = validityEntry;
return( status );
}
}
ENSURES( iterationCount < FAILSAFE_ITERATIONS_LARGE );
return( CRYPT_OK );
}
/****************************************************************************
* *
* Read/write RTCS Information *
* *
****************************************************************************/
/* Read/write an RTCS resquest entry:
Entry ::= SEQUENCE {
certHash OCTET STRING SIZE(20),
legacyID IssuerAndSerialNumber OPTIONAL
} */
CHECK_RETVAL STDC_NONNULL_ARG( ( 1 ) ) \
int sizeofRtcsRequestEntry( INOUT VALIDITY_INFO *rtcsEntry )
{
assert( isWritePtr( rtcsEntry, sizeof( VALIDITY_INFO ) ) );
return( ( int ) sizeofObject( sizeofObject( KEYID_SIZE ) ) );
}
CHECK_RETVAL STDC_NONNULL_ARG( ( 1, 2, 3 ) ) \
int readRtcsRequestEntry( INOUT STREAM *stream,
INOUT_PTR VALIDITY_INFO **listHeadPtrPtr,
INOUT CERT_INFO *certInfoPtr )
{
BYTE idBuffer[ CRYPT_MAX_HASHSIZE + 8 ];
int endPos, length, status;
assert( isWritePtr( stream, sizeof( STREAM ) ) );
assert( isWritePtr( listHeadPtrPtr, sizeof( VALIDITY_INFO * ) ) );
assert( isWritePtr( certInfoPtr, sizeof( CERT_INFO ) ) );
/* Determine the overall size of the entry */
status = readSequence( stream, &length );
if( cryptStatusError( status ) )
return( status );
endPos = stell( stream ) + length;
/* Read the certificate ID and add it to the validity information list */
status = readOctetString( stream, idBuffer, &length,
KEYID_SIZE, KEYID_SIZE );
if( cryptStatusOK( status ) && \
stell( stream ) <= endPos - MIN_ATTRIBUTE_SIZE )
{
/* Skip the legacy ID */
status = readUniversal( stream );
}
if( cryptStatusOK( status ) )
status = addValidityEntry( listHeadPtrPtr, NULL,
idBuffer, KEYID_SIZE );
return( status );
}
STDC_NONNULL_ARG( ( 1, 2 ) ) \
int writeRtcsRequestEntry( INOUT STREAM *stream,
const VALIDITY_INFO *rtcsEntry )
{
assert( isWritePtr( stream, sizeof( STREAM ) ) );
assert( isReadPtr( rtcsEntry, sizeof( VALIDITY_INFO ) ) );
/* Write the header and ID information */
writeSequence( stream, sizeofObject( KEYID_SIZE ) );
return( writeOctetString( stream, rtcsEntry->data, KEYID_SIZE,
DEFAULT_TAG ) );
}
/* Read/write an RTCS response entry:
Entry ::= SEQUENCE { -- basic response
certHash OCTET STRING SIZE(20),
status BOOLEAN
}
Entry ::= SEQUENCE { -- Full response
certHash OCTET STRING SIZE(20),
status ENUMERATED,
statusInfo ANY DEFINED BY status OPTIONAL,
extensions [0] Extensions OPTIONAL
} */
CHECK_RETVAL STDC_NONNULL_ARG( ( 1 ) ) \
int sizeofRtcsResponseEntry( INOUT VALIDITY_INFO *rtcsEntry,
const BOOLEAN isFullResponse )
{
assert( isWritePtr( rtcsEntry, sizeof( VALIDITY_INFO ) ) );
/* If it's a basic response the size is fairly easy to calculate */
if( !isFullResponse )
return( ( int ) sizeofObject( sizeofObject( KEYID_SIZE ) + \
sizeofBoolean() ) );
/* Remember the encoded attribute size for later when we write the
attributes */
rtcsEntry->attributeSize = sizeofAttributes( rtcsEntry->attributes );
return( ( int ) \
sizeofObject( sizeofObject( KEYID_SIZE ) + sizeofEnumerated( 1 ) + \
( ( rtcsEntry->attributeSize ) ? \
( int ) sizeofObject( rtcsEntry->attributeSize ) : 0 ) ) );
}
CHECK_RETVAL STDC_NONNULL_ARG( ( 1, 2, 3 ) ) \
int readRtcsResponseEntry( INOUT STREAM *stream,
INOUT_PTR VALIDITY_INFO **listHeadPtrPtr,
INOUT CERT_INFO *certInfoPtr,
const BOOLEAN isFullResponse )
{
VALIDITY_INFO *newEntry;
BYTE idBuffer[ CRYPT_MAX_HASHSIZE + 8 ];
int endPos, length, status;
assert( isWritePtr( stream, sizeof( STREAM ) ) );
assert( isWritePtr( listHeadPtrPtr, sizeof( VALIDITY_INFO * ) ) );
assert( isWritePtr( certInfoPtr, sizeof( CERT_INFO ) ) );
/* Determine the overall size of the entry */
status = readSequence( stream, &length );
if( cryptStatusError( status ) )
return( status );
endPos = stell( stream ) + length;
/* Read the ID information */
status = readOctetString( stream, idBuffer, &length, \
KEYID_SIZE, KEYID_SIZE );
if( cryptStatusError( status ) )
return( status );
/* Add the entry to the validity information list */
status = addValidityEntry( listHeadPtrPtr, &newEntry,
idBuffer, KEYID_SIZE );
if( cryptStatusError( status ) )
return( status );
/* Read the status information and record the valid/not-valid status */
if( isFullResponse )
{
status = readEnumerated( stream, &newEntry->extStatus );
if( cryptStatusOK( status ) )
{
newEntry->status = \
( newEntry->extStatus == CRYPT_CERTSTATUS_VALID ) ? \
TRUE : FALSE;
}
}
else
{
status = readBoolean( stream, &newEntry->status );
if( cryptStatusOK( status ) )
{
newEntry->extStatus = newEntry->status ? \
CRYPT_CERTSTATUS_VALID : CRYPT_CERTSTATUS_NOTVALID;
}
}
if( cryptStatusError( status ) || \
stell( stream ) > endPos - MIN_ATTRIBUTE_SIZE )
return( status );
/* Read the extensions. Since these are per-entry extensions we read
the wrapper here and read the extensions themselves as
CRYPT_CERTTYPE_NONE rather than CRYPT_CERTTYPE_RTCS to make sure
that they're processed as required */
status = readConstructed( stream, &length, 0 );
if( cryptStatusError( status ) )
return( status );
return( readAttributes( stream, &newEntry->attributes,
CRYPT_CERTTYPE_NONE, length,
&certInfoPtr->errorLocus,
&certInfoPtr->errorType ) );
}
STDC_NONNULL_ARG( ( 1, 2 ) ) \
int writeRtcsResponseEntry( INOUT STREAM *stream,
const VALIDITY_INFO *rtcsEntry,
const BOOLEAN isFullResponse )
{
int status;
assert( isWritePtr( stream, sizeof( STREAM ) ) );
assert( isReadPtr( rtcsEntry, sizeof( VALIDITY_INFO ) ) );
REQUIRES( rtcsEntry->extStatus >= CRYPT_CERTSTATUS_VALID && \
rtcsEntry->extStatus <= CRYPT_CERTSTATUS_UNKNOWN );
/* If it's a basic response it's a straightforward fixed-length
object */
if( !isFullResponse )
{
writeSequence( stream, sizeofObject( KEYID_SIZE ) +
sizeofBoolean() );
writeOctetString( stream, rtcsEntry->data, KEYID_SIZE, DEFAULT_TAG );
return( writeBoolean( stream, rtcsEntry->status, DEFAULT_TAG ) );
}
/* Write an extended response */
writeSequence( stream, sizeofObject( KEYID_SIZE ) + sizeofEnumerated( 1 ) );
writeOctetString( stream, rtcsEntry->data, KEYID_SIZE, DEFAULT_TAG );
status = writeEnumerated( stream, rtcsEntry->extStatus, DEFAULT_TAG );
if( cryptStatusError( status ) || rtcsEntry->attributeSize <= 0 )
return( status );
/* Write the per-entry extensions. Since these are per-entry extensions
we write them as CRYPT_CERTTYPE_NONE rather than CRYPT_CERTTYPE_RTCS
to make sure that they're processed as required */
return( writeAttributes( stream, rtcsEntry->attributes,
CRYPT_CERTTYPE_NONE, rtcsEntry->attributeSize ) );
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -