⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 certcget.c

📁 老外写的加密库cryptlib(版本3.1)
💻 C
📖 第 1 页 / 共 4 页
字号:
	HASHFUNCTION hashFunction;
	const int maxLength = *certInfoLength;
	int hashSize, issuerSerialDataSize, status;

	/* Get the hash algorithm information and hash the cert to get the cert 
	   ID if necessary */
	getHashParameters( CRYPT_ALGO_SHA, &hashFunction, &hashSize );
	if( !certInfoPtr->certHashSet )
		{
		hashFunction( NULL, certInfoPtr->certHash, certInfoPtr->certificate,
					  certInfoPtr->certificateSize, HASH_ALL );
		certInfoPtr->certHashSet = TRUE;
		}
	assert( certInfoPtr->serialNumber != NULL );

	/* Write the ESSCertID:

		ESSCertID ::= SEQUENCE {
			certHash		OCTET STRING SIZE(20),
			issuerSerial	SEQUENCE {
				issuer		SEQUENCE { [4] EXPLICIT Name },
				serial		INTEGER
				}
			} */
	issuerSerialDataSize = ( int ) \
			sizeofObject( sizeofObject( certInfoPtr->issuerDNsize ) ) + \
			sizeofInteger( certInfoPtr->serialNumber,
						   certInfoPtr->serialNumberLength );
	*certInfoLength = ( int ) \
			sizeofObject( sizeofObject( hashSize ) + \
						  sizeofObject( issuerSerialDataSize ) );
	if( certInfo == NULL )
		return( CRYPT_OK );
	if( *certInfoLength > maxLength )
		return( CRYPT_ERROR_OVERFLOW );
	sMemOpen( &stream, certInfo, *certInfoLength );
	writeSequence( &stream, sizeofObject( hashSize ) + \
							sizeofObject( issuerSerialDataSize ) );
	writeOctetString( &stream, certInfoPtr->certHash, hashSize, DEFAULT_TAG );
	writeSequence( &stream, issuerSerialDataSize );
	writeSequence( &stream, sizeofObject( certInfoPtr->issuerDNsize ) );
	writeConstructed( &stream, certInfoPtr->issuerDNsize, 4 );
	swrite( &stream, certInfoPtr->issuerDNptr, certInfoPtr->issuerDNsize );
	status = writeInteger( &stream, certInfoPtr->serialNumber,
						   certInfoPtr->serialNumberLength, DEFAULT_TAG );
	sMemDisconnect( &stream );
	assert( cryptStatusOK( status ) );

	return( status );
	}

/* Encode PKI user information into the external format and return it */

static int getPkiUserInfo( CERT_INFO *certInfoPtr, 
						   const CRYPT_ATTRIBUTE_TYPE certInfoType, 
						   void *certInfo, int *certInfoLength )
	{
	char encUserInfo[ 128 ];
	BYTE userInfo[ 128 ], *userInfoPtr = userInfo;
	const int maxLength = *certInfoLength;
	int userInfoLength = 128, status;

	if( certInfoType == CRYPT_CERTINFO_PKIUSER_ID )
		{
		status = getCertAttributeComponent( certInfoPtr,
											CRYPT_CERTINFO_SUBJECTKEYIDENTIFIER,
											userInfo, &userInfoLength );
		assert( cryptStatusOK( status ) );
		if( cryptStatusError( status ) )
			return( status );	/* Should never happen */
		}
	else
		userInfoPtr = ( certInfoType == CRYPT_CERTINFO_PKIUSER_ISSUEPASSWORD ) ? \
					  certInfoPtr->pkiIssuePW : certInfoPtr->pkiRevPW;
	*certInfoLength = encodePKIUserValue( encUserInfo, userInfoPtr,
				( certInfoType == CRYPT_CERTINFO_PKIUSER_ID ) ? 3 : 4 );
	zeroise( userInfo, 128 );
	if( certInfo == NULL )
		return( CRYPT_OK );
	if( *certInfoLength > maxLength )
		return( CRYPT_ERROR_OVERFLOW );
	memcpy( certInfo, encUserInfo, *certInfoLength );
	zeroise( encUserInfo, 128 );
	return( CRYPT_OK );
	}

/****************************************************************************
*																			*
*									Get a Component							*
*																			*
****************************************************************************/

/* Get a certificate component */

int getCertComponent( CERT_INFO *certInfoPtr,
					  const CRYPT_ATTRIBUTE_TYPE certInfoType,
					  void *certInfo, int *certInfoLength )
	{
	const int maxLength = ( certInfoLength != NULL ) ? *certInfoLength : 0;
	void *data = NULL;
	int *valuePtr = ( int * ) certInfo;
	int dataLength = 0;

	assert( ( certInfo == NULL && *certInfoLength == 0 ) || \
			( certInfoLength == NULL ) || \
			( *certInfoLength > 1 && *certInfoLength <= 32768 ) );

	/* If it's a GeneralName or DN component, return it.  These are 
	   special-case attribute values, so they have to come before the 
	   general attribute-handling code */
	if( isGeneralNameSelectionComponent( certInfoType ) )
		{
		SELECTION_STATE savedState;
		int status;

		/* Determine whether the given component is present or not.  This
		   has a somewhat odd status return since it returns the found/
		   notfound status in the return code as well as the returned value,
		   this mirrors the behaviour when reading extension-present
		   pseudo-attributes */
		saveSelectionState( savedState, certInfoPtr );
		status = selectGeneralName( certInfoPtr, certInfoType, 
									MAY_BE_ABSENT );
		if( cryptStatusOK( status ) )
			status = selectGeneralName( certInfoPtr, CRYPT_ATTRIBUTE_NONE, 
										MUST_BE_PRESENT );
		*valuePtr = cryptStatusOK( status ) ? TRUE : FALSE;
		restoreSelectionState( savedState, certInfoPtr );

		return( status );
		}
	if( isGeneralNameComponent( certInfoType ) )
		{
		ATTRIBUTE_LIST *attributeListPtr;
		int status;

		/* Find the requested GeneralName component and return it to the
		   caller */
		status = selectGeneralName( certInfoPtr, CRYPT_ATTRIBUTE_NONE,
									MUST_BE_PRESENT );
		if( cryptStatusError( status ) )
			return( status );
		attributeListPtr = findAttributeField( certInfoPtr->attributeCursor,
											   certInfoPtr->attributeCursor->fieldID,
											   certInfoType );
		if( attributeListPtr == NULL )
			return( CRYPT_ERROR_NOTFOUND );
		return( getCertAttributeComponentData( attributeListPtr, certInfo,
											   certInfoLength ) );
		}
	if( isDNComponent( certInfoType ) )
		{
		int status;

		/* Find the requested DN component and return it to the caller */
		status = selectDN( certInfoPtr, CRYPT_ATTRIBUTE_NONE,
						   MUST_BE_PRESENT );
		if( cryptStatusError( status ) )
			return( status );
		return( getDNComponentValue( *certInfoPtr->currentSelection.dnPtr,
									 certInfoType, certInfo, certInfoLength,
									 maxLength ) );
		}

	/* If it's standard cert or CMS attribute, return it */
	if( ( certInfoType >= CRYPT_CERTINFO_FIRST_EXTENSION && \
		  certInfoType <= CRYPT_CERTINFO_LAST_EXTENSION ) || \
		( certInfoType >= CRYPT_CERTINFO_FIRST_CMS && \
		  certInfoType <= CRYPT_CERTINFO_LAST_CMS ) )
		return( getCertAttributeComponent( certInfoPtr, certInfoType,
										   certInfo, certInfoLength ) );

	/* If it's anything else, handle it specially */
	switch( certInfoType )
		{
		case CRYPT_CERTINFO_SELFSIGNED:
			*valuePtr = ( certInfoPtr->flags & CERT_FLAG_SELFSIGNED ) ? \
						TRUE : FALSE;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_IMMUTABLE:
			*valuePtr = ( certInfoPtr->certificate != NULL ) ? TRUE: FALSE;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_XYZZY:
			{
			BYTE policyOID[ MAX_OID_SIZE ];
			int policyOIDLength = MAX_OID_SIZE;

			/* Check for the presence of the XYZZY policy OID */
			if( cryptStatusOK( \
				getCertAttributeComponent( certInfoPtr,
									CRYPT_CERTINFO_CERTPOLICYID,
									policyOID, &policyOIDLength ) ) && \
				policyOIDLength == sizeofOID( OID_CRYPTLIB_XYZZYCERT ) && \
				!memcmp( policyOID, OID_CRYPTLIB_XYZZYCERT, policyOIDLength ) )
				*valuePtr = TRUE;
			else
				*valuePtr = FALSE;
			return( CRYPT_OK );
			}
		case CRYPT_CERTINFO_CERTTYPE:
			*valuePtr = certInfoPtr->type;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_FINGERPRINT_MD5:
		case CRYPT_CERTINFO_FINGERPRINT_SHA:
			return( getCertHash( certInfoPtr, certInfoType, certInfo, 
								 certInfoLength ) );

		case CRYPT_CERTINFO_CURRENT_CERTIFICATE:
		case CRYPT_CERTINFO_CURRENT_EXTENSION:
		case CRYPT_CERTINFO_CURRENT_FIELD:
		case CRYPT_CERTINFO_CURRENT_COMPONENT:
			/* The current component and field are essentially the same 
			   thing since a component is one of a set of entries in a 
			   multivalued field, thus we only distinguish between 
			   extensions and everything else */
			if( certInfoPtr->attributeCursor == NULL )
				return( CRYPT_ERROR_NOTINITED );
			*valuePtr = ( certInfoType == CRYPT_CERTINFO_CURRENT_EXTENSION ) ? \
						certInfoPtr->attributeCursor->attributeID :
						certInfoPtr->attributeCursor->fieldID;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_TRUSTED_USAGE:
			if( certInfoPtr->trustedUsage == CRYPT_ERROR )
				return( CRYPT_ERROR_NOTFOUND );
			*valuePtr = certInfoPtr->trustedUsage;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_TRUSTED_IMPLICIT:
			*valuePtr = cryptStatusOK( \
							krnlSendMessage( certInfoPtr->ownerHandle,
											 IMESSAGE_SETATTRIBUTE,
											 &certInfoPtr->objectHandle,
											 CRYPT_IATTRIBUTE_CERT_CHECKTRUST ) ) ? \
						TRUE : FALSE;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_SIGNATURELEVEL:
			*valuePtr = certInfoPtr->signatureLevel;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_VERSION:
			*valuePtr = certInfoPtr->version;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_SERIALNUMBER:
			if( certInfoPtr->type == CRYPT_CERTTYPE_CRL )
				{
				const REVOCATION_INFO *revInfoPtr = \
					( certInfoPtr->currentRevocation != NULL ) ? \
					certInfoPtr->currentRevocation : certInfoPtr->revocations;

				if( revInfoPtr != NULL )
					{
					data = revInfoPtr->dataPtr;
					dataLength = revInfoPtr->dataLength;
					}
				}
			else
				{
				data = certInfoPtr->serialNumber;
				dataLength = certInfoPtr->serialNumberLength;
				}
			return( copyCertInfo( certInfo, certInfoLength, data, 
								  dataLength ) );

		case CRYPT_CERTINFO_ISSUERNAME:
			*valuePtr = ( certInfoPtr->issuerName != NULL ) ? TRUE : FALSE;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_VALIDFROM:
		case CRYPT_CERTINFO_THISUPDATE:
			if( certInfoPtr->startTime > 0 )
				{
				data = &certInfoPtr->startTime;
				dataLength = sizeof( time_t );
				}
			return( copyCertInfo( certInfo, certInfoLength, data, 
								  dataLength ) );

		case CRYPT_CERTINFO_VALIDTO:
		case CRYPT_CERTINFO_NEXTUPDATE:
			if( certInfoPtr->endTime > 0 )
				{
				data = &certInfoPtr->endTime;
				dataLength = sizeof( time_t );
				}
			return( copyCertInfo( certInfo, certInfoLength, data, 
								  dataLength ) );

		case CRYPT_CERTINFO_SUBJECTNAME:
			*valuePtr = ( certInfoPtr->subjectName != NULL ) ? TRUE : FALSE;
			return( CRYPT_OK );

		case CRYPT_CERTINFO_ISSUERUNIQUEID:
			return( copyCertInfo( certInfo, certInfoLength, 
								  certInfoPtr->issuerUniqueID, 
								  certInfoPtr->issuerUniqueIDlength ) );

		case CRYPT_CERTINFO_SUBJECTUNIQUEID:
			return( copyCertInfo( certInfo, certInfoLength, 
								  certInfoPtr->subjectUniqueID, 
								  certInfoPtr->subjectUniqueIDlength ) );

		case CRYPT_CERTINFO_REVOCATIONDATE:
			/* If there's a specific validity/revocation entry selected, get 
			   its invalidity/revocation time, otherwise if there are 
			   invalid/revoked certs present get the first cert's invalidity/
			   revocation time, otherwise get the default invalidity/
			   revocation time */
			if( certInfoPtr->type == CRYPT_CERTTYPE_RTCS_RESPONSE )
				data = ( certInfoPtr->currentValidity != NULL ) ? \
						   &certInfoPtr->currentValidity->invalidityTime : \
					   ( certInfoPtr->validityInfo != NULL ) ? \
						   &certInfoPtr->validityInfo->invalidityTime : \
					   ( certInfoPtr->revocationTime ) ? \
						   &certInfoPtr->revocationTime : NULL;
			else
				data = ( certInfoPtr->currentRevocation != NULL ) ? \
						   &certInfoPtr->currentRevocation->revocationTime : \
					   ( certInfoPtr->revocations != NULL ) ? \
						   &certInfoPtr->revocations->revocationTime : \
					   ( certInfoPtr->revocationTime ) ? \
						   &certInfoPtr->revocationTime : NULL;
			if( data != NULL )
				dataLength = sizeof( time_t );
			return( copyCertInfo( certInfo, certInfoLength, data, 
								  dataLength ) );

		case CRYPT_CERTINFO_CERTSTATUS:
			{
			const VALIDITY_INFO *valInfoPtr = \
					( certInfoPtr->currentValidity != NULL ) ? \
					certInfoPtr->currentValidity : certInfoPtr->validityInfo;

			if( valInfoPtr == NULL )
				return( CRYPT_ERROR_NOTFOUND );
			*valuePtr = valInfoPtr->extStatus;

			return( CRYPT_OK );
			}

		case CRYPT_CERTINFO_REVOCATIONSTATUS:
			{
			const REVOCATION_INFO *revInfoPtr = \
					( certInfoPtr->currentRevocation != NULL ) ? \
					certInfoPtr->currentRevocation : certInfoPtr->revocations;

			if( revInfoPtr == NULL )
				return( CRYPT_ERROR_NOTFOUND );
			*valuePtr = revInfoPtr->status;

			return( CRYPT_OK );
			}

		case CRYPT_CERTINFO_DN:
			{
			STREAM stream;
			int status;

			/* Export the entire DN in string form */
			status = selectDN( certInfoPtr, CRYPT_ATTRIBUTE_NONE,
							   MUST_BE_PRESENT );
			if( cryptStatusError( status ) )
				return( status );
			sMemOpen( &stream, certInfo, *certInfoLength );
			status = writeDNstring( &stream, 
									*certInfoPtr->currentSelection.dnPtr );
			if( cryptStatusOK( status ) )
				*certInfoLength = stell( &stream );
			sMemDisconnect( &stream );
			return( status );
			}

		case CRYPT_CERTINFO_PKIUSER_ID:
		case CRYPT_CERTINFO_PKIUSER_ISSUEPASSWORD:
		case CRYPT_CERTINFO_PKIUSER_REVPASSWORD:
			return( getPkiUserInfo( certInfoPtr, certInfoType, certInfo, 
									certInfoLength ) );

		case CRYPT_IATTRIBUTE_CRLENTRY:
			return( getCrlEntry( certInfoPtr, certInfo, certInfoLength ) );

		case CRYPT_IATTRIBUTE_SUBJECT:

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -