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

📄 cryptlib.c

📁 老外写的加密库cryptlib(版本3.1)
💻 C
📖 第 1 页 / 共 4 页
字号:
		}

	/* Verify ability to lock object and inability to change security 
	   parameters once locked */
	value = 5;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_PROPERTY_FORWARDCOUNT ) != CRYPT_OK || \
		krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, 
						 MESSAGE_VALUE_TRUE, 
						 CRYPT_PROPERTY_HIGHSECURITY ) != CRYPT_OK )
		{
		krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
		return( FALSE );
		}
	if( krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_PROPERTY_LOCKED ) != CRYPT_OK || \
		value != TRUE || \
		krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_PROPERTY_FORWARDCOUNT ) != CRYPT_ERROR_PERMISSION )
		{
		/* Object should be locked, forwardcount should be inaccessible */
		krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
		return( FALSE );
		}
	value = 1;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_PROPERTY_FORWARDCOUNT ) != CRYPT_ERROR_PERMISSION )
		{
		/* Security parameters shouldn't be writeable */
		krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
		return( FALSE );
		}

	krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );

	/* Create a cert object for the remaining kernel range checks */
	setMessageCreateObjectInfo( &createInfo, CRYPT_CERTTYPE_CERTIFICATE );
	status = krnlSendMessage( SYSTEM_OBJECT_HANDLE, IMESSAGE_DEV_CREATEOBJECT,
							  &createInfo, OBJECT_TYPE_CERTIFICATE );
	if( cryptStatusError( status ) )
		return( FALSE );
	cryptHandle = createInfo.cryptHandle;

	/* Verify functioning of kernel range checking, phase 3: Boolean values.
	   Any value should be OK, with conversion to TRUE/FALSE */
	value = 0;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK )
		status = CRYPT_ERROR;
	if( krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK || \
		value != FALSE )
		status = CRYPT_ERROR;
	value = 1;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK )
		status = CRYPT_ERROR;
	if( krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK || \
		value != TRUE )
		status = CRYPT_ERROR;
	value = 10000;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK )
		status = CRYPT_ERROR;
	if( krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK || \
		value != TRUE )
		status = CRYPT_ERROR;
	value = -1;
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK )
		status = CRYPT_ERROR;
	if( krnlSendMessage( cryptHandle, IMESSAGE_GETATTRIBUTE, &value, 
						 CRYPT_CERTINFO_SELFSIGNED ) != CRYPT_OK || \
		value != TRUE )
		status = CRYPT_ERROR;
	if( cryptStatusError( status ) )
		{
		krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
		return( FALSE );
		}

	/* Verify functioning of kernel range checking, phase 4: Time values,
	   Any value above the initial cutoff date should be OK */
	setMessageData( &msgData, &timeVal, sizeof( time_t ) );
	timeVal = -10;					/* Below (negative) */
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE_S, &msgData, 
						 CRYPT_CERTINFO_VALIDFROM ) != CRYPT_ARGERROR_STR1 )
		status = CRYPT_ERROR;
	timeVal = MIN_TIME_VALUE - 1;	/* Lower bound fencepost error */
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE_S, &msgData, 
						 CRYPT_CERTINFO_VALIDFROM ) != CRYPT_ARGERROR_STR1 )
		status = CRYPT_ERROR;
	timeVal = MIN_TIME_VALUE;		/* Lower bound */
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE_S, &msgData, 
						 CRYPT_CERTINFO_VALIDFROM ) != CRYPT_OK )
		status = CRYPT_ERROR;
	timeVal = 0x40000000L;			/* Mid-range */
	krnlSendMessage( cryptHandle, IMESSAGE_DELETEATTRIBUTE, NULL, 
					 CRYPT_CERTINFO_VALIDFROM );
	if( krnlSendMessage( cryptHandle, IMESSAGE_SETATTRIBUTE_S, &msgData, 
						 CRYPT_CERTINFO_VALIDFROM ) != CRYPT_OK )
		status = CRYPT_ERROR;
	if( cryptStatusError( status ) )
		{
		krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
		return( FALSE );
		}

	krnlSendNotifier( cryptHandle, IMESSAGE_DECREFCOUNT );
	return( TRUE );
	}

/****************************************************************************
*																			*
*							Startup/Shutdown Routines						*
*																			*
****************************************************************************/

/* The initialisation and shutdown actions performed for various object
   types.  The pre-init actions are used to handle various preparatory
   actions that are required before the actual init can be performed, for
   example to create the system device and user object, which are needed by
   the init routines.  The pre-shutdown actions are used to signal to various
   subsystems that a shutdown is about to occur, for example to allow the
   networking subsystem to gracefully exit from any currently occurring 
   network I/O.

   The order of the init/shutdown actions is:

					Object type		Action
					-----------		------
	Pre-init:		Device			Create system object

	Init:			User			Create default user object
					Keyset			Drivers - keysets
					Device			Drivers - devices
					Session			Drivers - networking

	Pre-shutdown:	Session			Networking - signal socket close
					Device			System object - signal entropy poll end

	Shutdown:		User			Destroy default user object	| Done by
					Device			Destroy system object		| kernel
					Keyset			Drivers - keysets
					Device			Drivers - devices
					Session			Drivers - networking

   The init order is determined by the following dependencies:

	All -> Device (System object handles many message types)
	User -> Cert (Default user object reads trusted certs)

   The shutdown order is determined by the following dependencies:

	Session (Networking needs to shut down to release any objects that are 
			 blocked waiting on network I/O)
	Device (System object needs to shut down ongoing entropy poll)

   After this the shutdown proper can take place.  The shutdown order is
   noncritical, provided the pre-shutdown actions have occurred.

   In theory the user and system objects are destroyed as part of the 
   standard shutdown, however the kernel prevents these objects from ever
   being explicitly destroyed so they're destroyed implicitly by the
   destroyObjects() cleanup call */

int certManagementFunction( const MANAGEMENT_ACTION_TYPE action );
int deviceManagementFunction( const MANAGEMENT_ACTION_TYPE action );
int keysetManagementFunction( const MANAGEMENT_ACTION_TYPE action );
int sessionManagementFunction( const MANAGEMENT_ACTION_TYPE action );
int userManagementFunction( const MANAGEMENT_ACTION_TYPE action );

typedef int ( *MANAGEMENT_FUNCTION )( const MANAGEMENT_ACTION_TYPE action );

static const MANAGEMENT_FUNCTION preInitFunctions[] = {
	deviceManagementFunction, NULL 
	};
static const MANAGEMENT_FUNCTION initFunctions[] = {
	userManagementFunction, NULL 
	};
static const MANAGEMENT_FUNCTION asyncInitFunctions[] = {
  #ifdef USE_KEYSETS
	keysetManagementFunction, 
  #endif /* USE_KEYSETS */
	deviceManagementFunction, 
  #ifdef USE_SESSIONS
	sessionManagementFunction, 
  #endif /* USE_SESSIONS */
	NULL 
	};
static const MANAGEMENT_FUNCTION preShutdownFunctions[] = {
  #ifdef USE_SESSIONS
	sessionManagementFunction, 
  #endif /* USE_SESSIONS */
	deviceManagementFunction, NULL 
	};
static const MANAGEMENT_FUNCTION shutdownFunctions[] = {
	/*userManagementFunction,*/ /*deviceManagementFunction,*/ 
  #ifdef USE_KEYSETS
	keysetManagementFunction, 
  #endif /* USE_KEYSETS */
	deviceManagementFunction, 
  #ifdef USE_SESSIONS
	sessionManagementFunction, 
  #endif /* USE_SESSIONS */
	NULL 
	};

/* Dispatch a set of management actions */

static int dispatchManagementAction( const MANAGEMENT_FUNCTION *mgmtFunctions,
									 const MANAGEMENT_ACTION_TYPE action )
	{
	int i, status = CRYPT_OK;

	for( i = 0; mgmtFunctions[ i ] != NULL; i++ )
		{
		const int localStatus = mgmtFunctions[ i ]( action );
		if( cryptStatusError( localStatus ) && cryptStatusOK( status ) )
			status = localStatus;
		}

	return( status );
	}

/* Under various OSes we bind to a number of drivers at runtime.  We can
   either do this sychronously or asynchronously depending on the setting of 
   a config option.  By default we use the async init since it speeds up the 
   startup.  Synchronisation is achieved by having the open/init functions in 
   the modules that require the drivers call waitSemaphore() on the driver 
   binding semaphore, which blocks until the drivers are bound if an async 
   bind is in progress, or returns immediately if no bind is in progress */

#ifdef USE_THREADS

THREADFUNC_DEFINE( threadedBind, dummy )
	{
	UNUSED( dummy );

	dispatchManagementAction( asyncInitFunctions, MANAGEMENT_ACTION_INIT );
	clearSemaphore( SEMAPHORE_DRIVERBIND );
	THREAD_EXIT();
	}
#endif /* USE_THREADS */

/* Initialise and shut down the system */

#if defined( __WIN32__ ) && defined( STATIC_LIB )
BOOLEAN isWin95;
#endif /* __WIN32__ && STATIC_LIB */

int initCryptlib( void )
	{
	int initLevel = 0, status;

	/* If the Win32 version is being compiled as a static .lib (not
	   recommended) we need to perform initialisation here.  Note that in
	   this form cryptlib is no longer fully thread-safe because we can't
	   guarantee that the thread-locking is automatically set up before
	   anything else */
#if defined( __WIN32__ ) && defined( STATIC_LIB )
	static DWORD dwPlatform = ( DWORD ) CRYPT_ERROR;

	/* Figure out which OS we're running under */
	if( dwPlatform == CRYPT_ERROR )
		{
		OSVERSIONINFO osvi = { sizeof( osvi ) };

		GetVersionEx( &osvi );
		dwPlatform = osvi.dwPlatformId;
		isWin95 = ( dwPlatform == VER_PLATFORM_WIN32_WINDOWS ) ? TRUE : FALSE;

		/* Check for Win32s just in case someone tries to load the DLL under
		   it */
		if( dwPlatform == VER_PLATFORM_WIN32s )
			return( CRYPT_ERROR );
		}
#endif /* __WIN32__ && STATIC_LIB */

	/* If we've already been initialised, don't do anything */
	if( !beginInitialisation( TRUE ) )
		return( CRYPT_OK );

	/* VisualAge C++ doesn't set the TZ correctly */
#if defined( __IBMC__ ) || defined( __IBMCPP__ )
	tzset();
#endif /* VisualAge C++ */

	/* Perform the multi-phase bootstrap */
	status = initInternalFunctions();
	assert( cryptStatusOK( status ) );
	if( cryptStatusOK( status ) )
		{
		initLevel = 1;
		status = dispatchManagementAction( preInitFunctions, 
										   MANAGEMENT_ACTION_PRE_INIT );
		assert( cryptStatusOK( status ) );
		}
	if( cryptStatusOK( status ) )
		{
		initLevel = 2;
		status = dispatchManagementAction( initFunctions, 
										   MANAGEMENT_ACTION_INIT );
		assert( cryptStatusOK( status ) );
		}
	if( cryptStatusOK( status ) )
		{
#ifdef USE_THREADS
		int asyncInit;
#endif /* USE_THREADS */

		initLevel = 3;

		/* Perform the final init phase asynchronously or synchronously 
		   depending on the config option setting.  We always send this 
		   query to the default user object since no other user objects 
		   exist at this time */
#ifdef USE_THREADS
		krnlSendMessage( DEFAULTUSER_OBJECT_HANDLE, IMESSAGE_GETATTRIBUTE, 
						 &asyncInit, CRYPT_OPTION_MISC_ASYNCINIT );
		if( asyncInit )
			{
			THREAD_HANDLE thread;
			THREAD_CREATE_VARS;

			/* Fire up the thread.  There's no problem with the thread 
			   exiting before we set the semaphore because it's a one-shot,
			   so if the thread gets there first the attempt to set the
			   semaphore below is ignored */
			status = THREAD_CREATE( threadedBind, NULL, thread );
			if( cryptStatusOK( status ) )
				setSemaphore( SEMAPHORE_DRIVERBIND, thread );
			else
				/* The thread couldn't be started, try again with a 
				   synchronous init */
				asyncInit = FALSE;
			}
		if( !asyncInit )
#endif /* USE_THREADS */
		status = dispatchManagementAction( asyncInitFunctions, 
										   MANAGEMENT_ACTION_INIT );
		assert( cryptStatusOK( status ) );
		}

	/* Everything's set up, verify that the general crypto algorithms and 
	   kernel security mechanisms are working as required */
	if( cryptStatusOK( status ) && \
		( !testGeneralAlgorithms() || !testKernelMechanisms() ) )
		{
		/* We should probably sound klaxons as well at this point */
		assert( NOTREACHED );
		status = CRYPT_ERROR_FAILED;
		}

⌨️ 快捷键说明

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