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

📄 res_env.c

📁 cryptlib安全工具包
💻 C
📖 第 1 页 / 共 3 页
字号:
	   using a stronger hash algorithm must also be able to verify the 
	   envelope using the stronger algorithm.  This allows a transparent 
	   upgrade to stronger hash algorithms as they become available */
	status = krnlSendMessage( iCryptHandle, IMESSAGE_GETATTRIBUTE,
							  &certHashAlgo, CRYPT_IATTRIBUTE_CERTHASHALGO );
	if( cryptStatusOK( status ) && \
		isStrongerHash( certHashAlgo, envelopeInfoPtr->defaultHash ) )
		envelopeInfoPtr->defaultHash = certHashAlgo;

	/* If there's no subject hash action available, create one so that we
	   can connect it to the signature action */
	if( envelopeInfoPtr->actionList == NULL )
		{
		MESSAGE_CREATEOBJECT_INFO createInfo;

		/* Create a default hash action */
		setMessageCreateObjectInfo( &createInfo, envelopeInfoPtr->defaultHash );
		status = krnlSendMessage( SYSTEM_OBJECT_HANDLE,
								  IMESSAGE_DEV_CREATEOBJECT, &createInfo,
								  OBJECT_TYPE_CONTEXT );
		if( cryptStatusError( status ) )
			return( status );

		/* Add the hash action to the list */
		status = addActionEx( &hashActionPtr, &envelopeInfoPtr->actionList,
							  envelopeInfoPtr->memPoolState, ACTION_HASH,
							  createInfo.cryptHandle );
		if( cryptStatusError( status ) )
			{
			krnlSendNotifier( createInfo.cryptHandle, IMESSAGE_DECREFCOUNT );
			return( status );
			}

		/* Remember that the action was added invisibly to the caller so that
		   we don't return an error if they add it explicitly later on */
		hashActionPtr->flags |= ACTION_ADDEDAUTOMATICALLY;
		}
	else
		{
		/* Find the last hash action that was added */
		hashActionPtr = findLastAction( envelopeInfoPtr->actionList,
										ACTION_HASH );
		if( hashActionPtr == NULL )
			{
			setErrorInfo( envelopeInfoPtr, CRYPT_ENVINFO_HASH,
						  CRYPT_ERRTYPE_ATTR_ABSENT );
			return( CRYPT_ERROR_NOTINITED );
			}
		}

	/* Connect the signature action to the last hash action that was added
	   and remember that this action now has a controlling action */
	actionListPtr->associatedAction = hashActionPtr;
	hashActionPtr->flags &= ~ACTION_NEEDSCONTROLLER;

	return( CRYPT_OK );
	}

/****************************************************************************
*																			*
*					Enveloping Information Management Functions				*
*																			*
****************************************************************************/

/* Add enveloping information to an envelope */

CHECK_RETVAL STDC_NONNULL_ARG( ( 1 ) ) \
static int addEnvelopeInfo( INOUT ENVELOPE_INFO *envelopeInfoPtr,
							IN_ATTRIBUTE const CRYPT_ATTRIBUTE_TYPE envInfo,
							IN_INT_Z const int value )
	{
	CRYPT_HANDLE cryptHandle = ( CRYPT_HANDLE ) value;
	ACTION_LIST *actionListPtr;

	assert( isWritePtr( envelopeInfoPtr, sizeof( ENVELOPE_INFO ) ) );

	REQUIRES( ( envInfo == CRYPT_IATTRIBUTE_INCLUDESIGCERT ) || \
			  ( envInfo == CRYPT_IATTRIBUTE_ATTRONLY ) || \
			  ( envInfo > CRYPT_ENVINFO_FIRST && \
				envInfo < CRYPT_ENVINFO_LAST ) );

	/* If it's a generic "add a context" action for a PGP envelope check 
	   that everything is valid.  This is necessary because the PGP format 
	   doesn't support the full range of enveloping capabilities */
#ifdef USE_PGP
	if( envelopeInfoPtr->type == CRYPT_FORMAT_PGP && \
		envInfo > CRYPT_ENVINFO_FIRST && \
		envInfo < CRYPT_ENVINFO_LAST )
		{
		const int status = checkPgpUsage( envelopeInfoPtr, envInfo );
		if( cryptStatusError( status ) )
			{
			setErrorInfo( envelopeInfoPtr, envInfo,
						  CRYPT_ERRTYPE_ATTR_PRESENT );
			return( status );
			}
		}
#endif /* USE_PGP */

	/* If it's meta-information, remember the value */
	switch( envInfo )
		{
		case CRYPT_IATTRIBUTE_INCLUDESIGCERT:
			/* This is on by default so we should only be turning it off */
			REQUIRES( value == FALSE );

			envelopeInfoPtr->flags |= ENVELOPE_NOSIGNINGCERTS;
			return( CRYPT_OK );

		case CRYPT_IATTRIBUTE_ATTRONLY:
			/* This is off by default so we should only be turning it on */
			REQUIRES( value == TRUE );

			/* Detached-signature and attribute-only messages are mutually 
			   exclusive */
			if( envelopeInfoPtr->flags & ENVELOPE_DETACHED_SIG )
				{
				setErrorInfo( envelopeInfoPtr, CRYPT_ENVINFO_DETACHEDSIGNATURE,
							  CRYPT_ERRTYPE_ATTR_PRESENT );
				return( CRYPT_ERROR_INITED );
				}
			envelopeInfoPtr->flags |= ENVELOPE_ATTRONLY;
			return( CRYPT_OK );

		case CRYPT_ENVINFO_DATASIZE:
			envelopeInfoPtr->payloadSize = value;
			return( CRYPT_OK );

		case CRYPT_ENVINFO_CONTENTTYPE:
			envelopeInfoPtr->contentType = value;
			return( CRYPT_OK );

		case CRYPT_ENVINFO_DETACHEDSIGNATURE:
			if( value )
				{
				/* Detached-signature and attribute-only messages are 
				   mutually exclusive.  Since the attribute-only message 
				   attribute is internal we can't set extended error 
				   information for this one */
				if( envelopeInfoPtr->flags & ENVELOPE_ATTRONLY )
					return( CRYPT_ERROR_INITED );
				envelopeInfoPtr->flags |= ENVELOPE_DETACHED_SIG;
				}
			else
				envelopeInfoPtr->flags &= ~ENVELOPE_DETACHED_SIG;
			return( CRYPT_OK );

		case CRYPT_ENVINFO_INTEGRITY:
			switch( value )
				{
				case CRYPT_INTEGRITY_NONE:
					return( CRYPT_OK );

				case CRYPT_INTEGRITY_MACONLY:
					envelopeInfoPtr->usage = ACTION_MAC;
					return( CRYPT_OK );

				case CRYPT_INTEGRITY_FULL:
					envelopeInfoPtr->usage = ACTION_CRYPT;
					envelopeInfoPtr->flags |= ENVELOPE_AUTHENC;
					return( CRYPT_OK );
				}
			retIntError();

		case CRYPT_ENVINFO_KEYSET_SIGCHECK:
		case CRYPT_ENVINFO_KEYSET_ENCRYPT:
		case CRYPT_ENVINFO_KEYSET_DECRYPT:
			/* It's keyset information, just keep a record of it for later 
			   use */
			return( addKeysetInfo( envelopeInfoPtr, envInfo, cryptHandle ) );

		case CRYPT_ENVINFO_SIGNATURE_EXTRADATA:
		case CRYPT_ENVINFO_TIMESTAMP:
			{
			CRYPT_HANDLE *iCryptHandlePtr;

			/* Find the last signature action that was added and make sure
			   that it doesn't already have an action of this type attached 
			   to it */
			actionListPtr = findLastAction( envelopeInfoPtr->postActionList,
											ACTION_SIGN );
			if( actionListPtr == NULL )
				{
				setErrorInfo( envelopeInfoPtr, CRYPT_ENVINFO_SIGNATURE,
							  CRYPT_ERRTYPE_ATTR_ABSENT );
				return( CRYPT_ERROR_NOTINITED );
				}
			iCryptHandlePtr = ( envInfo == CRYPT_ENVINFO_SIGNATURE_EXTRADATA ) ? \
							  &actionListPtr->iExtraData : \
							  &actionListPtr->iTspSession;
			if( *iCryptHandlePtr != CRYPT_ERROR )
				{
				setErrorInfo( envelopeInfoPtr, envInfo,
							  CRYPT_ERRTYPE_ATTR_PRESENT );
				return( CRYPT_ERROR_INITED );
				}

			/* Increment its reference count and add it to the action */
			krnlSendNotifier( cryptHandle, IMESSAGE_INCREFCOUNT );
			*iCryptHandlePtr = cryptHandle;
			return( CRYPT_OK );
			}

		case CRYPT_ENVINFO_ORIGINATOR:
#ifdef USE_FORTEZZA
			/* If there's a session key present make sure that it's 
			   consistent with the originator info */
			if( envelopeInfoPtr->iCryptContext != CRYPT_ERROR )
				{
				int status;

				status = checkFortezzaUsage( cryptHandle, envelopeInfoPtr,
											 CRYPT_ENVINFO_ORIGINATOR );
				if( cryptStatusError( status ) )
					return( status );
				}

			/* Increment its reference count and add it to the action */
			krnlSendNotifier( cryptHandle, IMESSAGE_INCREFCOUNT );
			envelopeInfoPtr->iExtraCertChain = cryptHandle;

			/* Since we're using Fortezza key management we have to use 
			   Skipjack as the data encryption algorithm */
			envelopeInfoPtr->defaultAlgo = CRYPT_ALGO_SKIPJACK;

			return( CRYPT_OK );
#else
			return( CRYPT_ARGERROR_NUM1 );
#endif /* USE_FORTEZZA */

		case CRYPT_ENVINFO_COMPRESSION:
#ifdef USE_COMPRESSION
			/* Make sure that we don't try and initialise the compression
			   multiple times */
			if( envelopeInfoPtr->flags & ENVELOPE_ZSTREAMINITED )
				{
				setErrorInfo( envelopeInfoPtr, CRYPT_ENVINFO_COMPRESSION,
							  CRYPT_ERRTYPE_ATTR_PRESENT );
				return( CRYPT_ERROR_INITED );
				}

			/* Initialize the compression */
			if( deflateInit( &envelopeInfoPtr->zStream, \
							 Z_DEFAULT_COMPRESSION ) != Z_OK )
				return( CRYPT_ERROR_MEMORY );
			envelopeInfoPtr->flags |= ENVELOPE_ZSTREAMINITED;

			return( CRYPT_OK );
#else
			return( CRYPT_ARGERROR_NUM1 );
#endif /* USE_COMPRESSION */

		case CRYPT_ENVINFO_PUBLICKEY:
		case CRYPT_ENVINFO_PRIVATEKEY:
			return( addContextInfo( envelopeInfoPtr, cryptHandle,
									&envelopeInfoPtr->preActionList,
									ACTION_KEYEXCHANGE_PKC ) );

		case CRYPT_ENVINFO_KEY:
			/* PGP doesn't allow KEK-based encryption so if it's a PGP
			   envelope we drop through and treat it as a session key */
			if( envelopeInfoPtr->type != CRYPT_FORMAT_PGP )
				{
				return( addContextInfo( envelopeInfoPtr, cryptHandle, 
										&envelopeInfoPtr->preActionList,
										ACTION_KEYEXCHANGE ) );
				}
			/* Fall through */

		case CRYPT_ENVINFO_SESSIONKEY:
			/* We can't add more than one session key */
			if( envelopeInfoPtr->actionList != NULL )
				{
				setErrorInfo( envelopeInfoPtr, CRYPT_ENVINFO_SESSIONKEY,
							  CRYPT_ERRTYPE_ATTR_PRESENT );
				return( CRYPT_ERROR_INITED );
				}

#ifdef USE_FORTEZZA
			/* If there's originator info present make sure that it's
			   consistent with the new session key */
			if( envelopeInfoPtr->iExtraCertChain != CRYPT_ERROR )
				{
				int status;

				status = checkFortezzaUsage( cryptHandle, envelopeInfoPtr,
											 CRYPT_ENVINFO_SESSIONKEY );
				if( cryptStatusError( status ) )
					return( status );
				}
#endif /* USE_FORTEZZA */

			return( addContextInfo( envelopeInfoPtr, cryptHandle, 
									&envelopeInfoPtr->actionList,
									ACTION_CRYPT ) );

		case CRYPT_ENVINFO_HASH:
			return( addContextInfo( envelopeInfoPtr, cryptHandle, 
									&envelopeInfoPtr->actionList, 
									ACTION_HASH ) );

		case CRYPT_ENVINFO_SIGNATURE:
			return( addContextInfo( envelopeInfoPtr, cryptHandle, 
									&envelopeInfoPtr->postActionList, 
									ACTION_SIGN ) );
		}

	retIntError();
	}

CHECK_RETVAL STDC_NONNULL_ARG( ( 1 ) ) \
static int addEnvelopeInfoString( INOUT ENVELOPE_INFO *envelopeInfoPtr,
								  IN_RANGE( CRYPT_ENVINFO_PASSWORD, \
											CRYPT_ENVINFO_PASSWORD ) \
									const CRYPT_ATTRIBUTE_TYPE envInfo,
								  IN_BUFFER( valueLength ) const void *value, 
								  IN_RANGE( 1, CRYPT_MAX_TEXTSIZE ) \
									const int valueLength )
	{
	assert( isWritePtr( envelopeInfoPtr, sizeof( ENVELOPE_INFO ) ) );
	assert( isReadPtr( value, valueLength ) );

	REQUIRES( envInfo == CRYPT_ENVINFO_PASSWORD );
	REQUIRES( valueLength > 0 && valueLength <= CRYPT_MAX_TEXTSIZE );

#ifdef USE_PGP
	if( envelopeInfoPtr->type == CRYPT_FORMAT_PGP )
		return( addPgpPasswordInfo( envelopeInfoPtr, value, valueLength ) );
#endif /* USE_PGP */
	return( addPasswordInfo( envelopeInfoPtr, value, valueLength ) );
	}

/****************************************************************************
*																			*
*							Envelope Access Routines						*
*																			*
****************************************************************************/

STDC_NONNULL_ARG( ( 1 ) ) \
void initEnvResourceHandling( INOUT ENVELOPE_INFO *envelopeInfoPtr )
	{
	assert( isWritePtr( envelopeInfoPtr, sizeof( ENVELOPE_INFO ) ) );

	REQUIRES_V( !( envelopeInfoPtr->flags & ENVELOPE_ISDEENVELOPE ) );

	/* Set the access method pointers */
	envelopeInfoPtr->addInfo = addEnvelopeInfo;
	envelopeInfoPtr->addInfoString = addEnvelopeInfoString;
	envelopeInfoPtr->checkMissingInfo = checkMissingInfo;
	}
#endif /* USE_ENVELOPES */

⌨️ 快捷键说明

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