📄 timing.c
字号:
( long ) ( timeCorrSum10 / timesCount10 ) );
else
if( noTimes <= 2 && i == 1 )
printf( "Priv: min.= %d, avg.= %d ", ( long ) timeMin,
( long ) ( timeCorrSum10 / timesCount10 ) );
else
printf( "%6d", ( long ) ( timeCorrSum10 / timesCount10 ) );
#if 0 /* Print difference to fastest time, usually only around 1% */
printf( "(%4d)", ( timeCorrSum10 / timesCount10 ) - timeMin );
#endif /* 0 */
#ifdef USE_SD
/* Find the standard deviation */
for( j = 1; j < NO_TESTS + 1; j++ )
{
const HIRES_TIME timeDev = times[ j ][ i ] - timeAvg;
timeCorrSumSD += ( timeDev * timeDev );
}
stdDev = timeCorrSumSD / NO_TESTS;
stdDev = sqrt( stdDev );
/* Find the mean time, discarding anomalous results more than two
standard deviations out */
timeCorrSumSD = 0;
timeDelta = ( HIRES_TIME ) stdDev * 2;
for( j = 1; j < NO_TESTS + 1; j++ )
if( times[ j ][ i ] > timeAvg - timeDelta && \
times[ j ][ i ] < timeAvg + timeDelta )
{
timeCorrSumSD += times[ j ][ i ];
timesCountSD++;
}
if( timesCountSD == 0 )
timesCountSD++; /* Context switch, fudge it */
printf( "%6d", timeCorrSumSD / timesCountSD );
#if 1 /* Print difference to fastest and mean times, usually only around
1% */
printf( " (dF = %4d, dM = %4d)\n",
( timeCorrSumSD / timesCountSD ) - timeMin,
abs( ( timeCorrSumSD / timesCountSD ) - \
( timeCorrSum10 / timesCount10 ) ) );
#endif /* 0 */
#endif /* USE_SD */
}
printf( "\n" );
}
static HIRES_TIME encOne( const CRYPT_CONTEXT cryptContext,
BYTE *buffer, const int length )
{
HIRES_TIME timeVal;
int status;
memset( buffer, '*', length );
timeVal = timeDiff( 0 );
status = cryptEncrypt( cryptContext, buffer, length );
return( timeDiff( timeVal ) );
}
static void encTest( const CRYPT_CONTEXT cryptContext,
const CRYPT_ALGO_TYPE cryptAlgo, BYTE *buffer,
HIRES_TIME times[] )
{
int index = 0;
times[ index++ ] = ( cryptAlgo != CRYPT_ALGO_AES ) ? \
encOne( cryptContext, buffer, 8 ) : 0;
times[ index++ ] = encOne( cryptContext, buffer, 16 );
times[ index++ ] = encOne( cryptContext, buffer, 64 );
times[ index++ ] = encOne( cryptContext, buffer, 1024 );
times[ index++ ] = encOne( cryptContext, buffer, 4096 );
times[ index++ ] = encOne( cryptContext, buffer, 8192 );
times[ index++ ] = encOne( cryptContext, buffer, 65536L );
}
static int encTests( const CRYPT_DEVICE cryptDevice,
const CRYPT_ALGO_TYPE cryptAlgo,
const CRYPT_ALGO_TYPE cryptMode,
BYTE *buffer )
{
CRYPT_CONTEXT cryptContext;
HIRES_TIME times[ NO_TESTS + 1 ][ 8 ], timeVal, timeSum = 0;
int i, status;
memset( buffer, 0, 100000L );
/* Set up the context for use */
if( !checkLowlevelInfo( cryptDevice, cryptAlgo ) )
return( FALSE );
for( i = 0; i < 10; i++ )
{
timeVal = timeDiff( 0 );
status = loadContexts( &cryptContext, NULL, cryptDevice,
cryptAlgo, cryptMode,
( BYTE * ) "12345678901234567890",
( cryptAlgo == CRYPT_ALGO_DES ) ? 8 : \
( cryptAlgo == CRYPT_ALGO_3DES || \
cryptAlgo == CRYPT_ALGO_RC4 || \
cryptAlgo == CRYPT_ALGO_AES ) ? 16 : 0 );
timeVal = timeDiff( timeVal );
if( status == CRYPT_ERROR_NOTAVAIL || !status )
return( FALSE );
timeSum += timeVal;
if( i < 9 )
cryptDestroyContext( cryptContext );
}
printf( "setup time = %d ticks.\n", timeSum / 10 );
puts( " 8 16 64 1K 4K 8K 64K" );
puts( " ---- ---- ---- ---- ---- ---- ----" );
/* Run the encryption tests NO_TESTS times, discarding the first set
of results since the cache will be empty at that point */
for( i = 0; i < NO_TESTS + 1; i++ )
encTest( cryptContext, cryptAlgo, buffer, times[ i ] );
printTimes( times, 7 );
/* Re-run the encryption tests with a 1-byte misalignment */
for( i = 0; i < NO_TESTS + 1; i++ )
encTest( cryptContext, cryptAlgo, buffer + 1, times[ i ] );
printTimes( times, 7 );
/* Re-run the encryption tests with a 4-byte misalignment */
for( i = 0; i < NO_TESTS + 1; i++ )
encTest( cryptContext, cryptAlgo, buffer + 4, times[ i ] );
printTimes( times, 7 );
/* Re-run the test 1000 times with various buffer alignments */
timeVal = 0;
for( i = 0; i < 1000; i++ )
timeVal += encOne( cryptContext, buffer, 1024 );
printf( "Aligned: %d ", timeVal / 1000 );
timeVal = 0;
for( i = 0; i < 1000; i++ )
timeVal += encOne( cryptContext, buffer + 1, 1024 );
printf( "misaligned + 1: %d ", timeVal / 1000 );
timeVal = 0;
for( i = 0; i < 1000; i++ )
timeVal += encOne( cryptContext, buffer + 4, 1024 );
printf( "misaligned + 4: %d.\n", timeVal / 1000 );
return( TRUE );
}
static void performanceTests( const CRYPT_DEVICE cryptDevice )
{
BYTE *buffer;
if( ( buffer = malloc( 100000L ) ) == NULL )
{
puts( "Couldn't 100K allocate test buffer." );
return;
}
encTests( cryptDevice, CRYPT_ALGO_DES, CRYPT_MODE_ECB, buffer );
encTests( cryptDevice, CRYPT_ALGO_DES, CRYPT_MODE_CBC, buffer );
encTests( cryptDevice, CRYPT_ALGO_3DES, CRYPT_MODE_ECB, buffer );
encTests( cryptDevice, CRYPT_ALGO_3DES, CRYPT_MODE_CBC, buffer );
encTests( cryptDevice, CRYPT_ALGO_RC4, CRYPT_MODE_OFB, buffer );
encTests( cryptDevice, CRYPT_ALGO_AES, CRYPT_MODE_CBC, buffer );
encTests( cryptDevice, CRYPT_ALGO_MD5, CRYPT_MODE_NONE, buffer );
encTests( cryptDevice, CRYPT_ALGO_SHA, CRYPT_MODE_NONE, buffer );
free( buffer );
}
/****************************************************************************
* *
* PKC Timing Tests *
* *
****************************************************************************/
/* Timing tests for PKC crypto operations. Since the DH operations aren't
visible externally, we have to use the kernel API to perform the timing
test. To get the necessary definitions and prototypes, we have to use
crypt.h, however since we've already included cryptlib.h the built-in
guards preclude us from pulling it in again with the internal-only values
defined, so we have to explicitly define things like attribute values
that normally aren't visible externally */
#undef __WINDOWS__
#undef __WIN16__
#undef __WIN32__
#undef BYTE
#undef BOOLEAN
#ifdef _MSC_VER
#define INC_CHILD
#include "../crypt.h"
#else
#include "crypt.h"
#endif /* Braindamaged MSC include handling */
#define CRYPT_IATTRIBUTE_KEY_SPKI 8015
static const BYTE dh1024SPKI[] = {
0x30, 0x82, 0x01, 0x21,
0x30, 0x82, 0x01, 0x17,
0x06, 0x07, 0x2A, 0x86, 0x48, 0xCE, 0x3E, 0x02, 0x01,
0x30, 0x82, 0x01, 0x0A,
0x02, 0x81, 0x81, 0x00, /* p */
0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
0xC9, 0x0F, 0xDA, 0xA2, 0x21, 0x68, 0xC2, 0x34,
0xC4, 0xC6, 0x62, 0x8B, 0x80, 0xDC, 0x1C, 0xD1,
0x29, 0x02, 0x4E, 0x08, 0x8A, 0x67, 0xCC, 0x74,
0x02, 0x0B, 0xBE, 0xA6, 0x3B, 0x13, 0x9B, 0x22,
0x51, 0x4A, 0x08, 0x79, 0x8E, 0x34, 0x04, 0xDD,
0xEF, 0x95, 0x19, 0xB3, 0xCD, 0x3A, 0x43, 0x1B,
0x30, 0x2B, 0x0A, 0x6D, 0xF2, 0x5F, 0x14, 0x37,
0x4F, 0xE1, 0x35, 0x6D, 0x6D, 0x51, 0xC2, 0x45,
0xE4, 0x85, 0xB5, 0x76, 0x62, 0x5E, 0x7E, 0xC6,
0xF4, 0x4C, 0x42, 0xE9, 0xA6, 0x37, 0xED, 0x6B,
0x0B, 0xFF, 0x5C, 0xB6, 0xF4, 0x06, 0xB7, 0xED,
0xEE, 0x38, 0x6B, 0xFB, 0x5A, 0x89, 0x9F, 0xA5,
0xAE, 0x9F, 0x24, 0x11, 0x7C, 0x4B, 0x1F, 0xE6,
0x49, 0x28, 0x66, 0x51, 0xEC, 0xE6, 0x53, 0x81,
0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
0x02, 0x01, /* g */
0x02,
0x02, 0x81, 0x80, /* q */
0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
0xE4, 0x87, 0xED, 0x51, 0x10, 0xB4, 0x61, 0x1A,
0x62, 0x63, 0x31, 0x45, 0xC0, 0x6E, 0x0E, 0x68,
0x94, 0x81, 0x27, 0x04, 0x45, 0x33, 0xE6, 0x3A,
0x01, 0x05, 0xDF, 0x53, 0x1D, 0x89, 0xCD, 0x91,
0x28, 0xA5, 0x04, 0x3C, 0xC7, 0x1A, 0x02, 0x6E,
0xF7, 0xCA, 0x8C, 0xD9, 0xE6, 0x9D, 0x21, 0x8D,
0x98, 0x15, 0x85, 0x36, 0xF9, 0x2F, 0x8A, 0x1B,
0xA7, 0xF0, 0x9A, 0xB6, 0xB6, 0xA8, 0xE1, 0x22,
0xF2, 0x42, 0xDA, 0xBB, 0x31, 0x2F, 0x3F, 0x63,
0x7A, 0x26, 0x21, 0x74, 0xD3, 0x1B, 0xF6, 0xB5,
0x85, 0xFF, 0xAE, 0x5B, 0x7A, 0x03, 0x5B, 0xF6,
0xF7, 0x1C, 0x35, 0xFD, 0xAD, 0x44, 0xCF, 0xD2,
0xD7, 0x4F, 0x92, 0x08, 0xBE, 0x25, 0x8F, 0xF3,
0x24, 0x94, 0x33, 0x28, 0xF6, 0x73, 0x29, 0xC0,
0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
0x03, 0x04, 0x00,
0x02, 0x01, 0x00 }; /* y */
static BOOLEAN loadDHKey( CRYPT_CONTEXT *cryptContext )
{
int status;
/* Create the DH context */
status = cryptCreateContext( cryptContext, CRYPT_UNUSED, CRYPT_ALGO_DH );
if( cryptStatusError( status ) )
{
printf( "cryptCreateContext() failed with error code %d.\n",
status );
return( FALSE );
}
cryptSetAttributeString( *cryptContext, CRYPT_CTXINFO_LABEL,
"DH key", strlen( "DH key" ) );
if( cryptStatusOK( status ) )
{
RESOURCE_DATA msgData;
setMessageData( &msgData, ( void * ) dh1024SPKI,
sizeof( dh1024SPKI ) );
#if 0
status = krnlSendMessage( *cryptContext, IMESSAGE_SETATTRIBUTE_S,
&msgData, CRYPT_IATTRIBUTE_KEY_SPKI );
#else
status = cryptDeviceQueryCapability( *cryptContext, 1000,
( CRYPT_QUERY_INFO * ) &msgData );
#endif /* 0 */
}
if( cryptStatusError( status ) )
{
printf( "DH key load failed, status = %d, line %d.\n", status,
__LINE__ );
return( FALSE );
}
return( TRUE );
}
typedef struct {
const int nLen; const BYTE n[ 128 ];
const int eLen; const BYTE e[ 3 ];
const int dLen; const BYTE d[ 128 ];
const int pLen; const BYTE p[ 64 ];
const int qLen; const BYTE q[ 64 ];
const int uLen; const BYTE u[ 64 ];
const int e1Len; const BYTE e1[ 64 ];
const int e2Len; const BYTE e2[ 64 ];
} RSA_KEY;
static const RSA_KEY rsa1024Key = {
/* n */
1024,
{ 0x9C, 0x4D, 0x98, 0x18, 0x67, 0xF9, 0x45, 0xBC,
0xB6, 0x75, 0x53, 0x5D, 0x2C, 0xFA, 0x55, 0xE4,
0x51, 0x54, 0x9F, 0x0C, 0x16, 0xB1, 0xAF, 0x89,
0xF6, 0xF3, 0xE7, 0x78, 0xB1, 0x2B, 0x07, 0xFB,
0xDC, 0xDE, 0x64, 0x23, 0x34, 0x87, 0xDA, 0x0B,
0xE5, 0xB3, 0x17, 0x16, 0xA4, 0xE3, 0x7F, 0x23,
0xDF, 0x96, 0x16, 0x28, 0xA6, 0xD2, 0xF0, 0x0A,
0x59, 0xEE, 0x06, 0xB3, 0x76, 0x6C, 0x64, 0x19,
0xD9, 0x76, 0x41, 0x25, 0x66, 0xD1, 0x93, 0x51,
0x52, 0x06, 0x6B, 0x71, 0x50, 0x0E, 0xAB, 0x30,
0xA5, 0xC8, 0x41, 0xFC, 0x30, 0xBC, 0x32, 0xD7,
0x4B, 0x22, 0xF2, 0x45, 0x4C, 0x94, 0x68, 0xF1,
0x92, 0x8A, 0x4C, 0xF9, 0xD4, 0x5E, 0x87, 0x92,
0xA8, 0x54, 0x93, 0x92, 0x94, 0x48, 0xA4, 0xA3,
0xEE, 0x19, 0x7F, 0x6E, 0xD3, 0x14, 0xB1, 0x48,
0xCE, 0x93, 0xD1, 0xEA, 0x4C, 0xE1, 0x9D, 0xEF },
/* e */
17,
{ 0x01, 0x00, 0x01 },
/* d */
1022,
{ 0x37, 0xE2, 0x66, 0x67, 0x13, 0x85, 0xC4, 0xB1,
0x5C, 0x6B, 0x46, 0x8B, 0x21, 0xF1, 0xBF, 0x94,
0x0A, 0xA0, 0x3E, 0xDD, 0x8B, 0x9F, 0xAC, 0x2B,
0x9F, 0xE8, 0x44, 0xF2, 0x9A, 0x25, 0xD0, 0x8C,
0xF4, 0xC3, 0x6E, 0xFA, 0x47, 0x65, 0xEB, 0x48,
0x25, 0xB0, 0x8A, 0xA8, 0xC5, 0xFB, 0xB1, 0x11,
0x9A, 0x77, 0x87, 0x24, 0xB1, 0xC0, 0xE9, 0xA2,
0x49, 0xD5, 0x19, 0x00, 0x41, 0x6F, 0x2F, 0xBA,
0x9F, 0x28, 0x47, 0xF9, 0xB8, 0xBA, 0xFF, 0xF4,
0x8B, 0x20, 0xC9, 0xC9, 0x39, 0xAB, 0x52, 0x0E,
0x8A, 0x5A, 0xAF, 0xB3, 0xA3, 0x93, 0x4D, 0xBB,
0xFE, 0x62, 0x9B, 0x02, 0xCC, 0xA7, 0xB4, 0xAE,
0x86, 0x65, 0x88, 0x19, 0xD7, 0x44, 0xA7, 0xE4,
0x18, 0xB6, 0xCE, 0x01, 0xCD, 0xDF, 0x36, 0x81,
0xD5, 0xE1, 0x62, 0xF8, 0xD0, 0x27, 0xF1, 0x86,
0xA8, 0x58, 0xA7, 0xEB, 0x39, 0x79, 0x56, 0x41 },
/* p */
512,
{ 0xCF, 0xDA, 0xF9, 0x99, 0x6F, 0x05, 0x95, 0x84,
0x09, 0x90, 0xB3, 0xAB, 0x39, 0xB7, 0xDD, 0x1D,
0x7B, 0xFC, 0xFD, 0x10, 0x35, 0xA0, 0x18, 0x1D,
0x9A, 0x11, 0x30, 0x90, 0xD4, 0x3B, 0xF0, 0x5A,
0xC1, 0xA6, 0xF4, 0x53, 0xD0, 0x94, 0xA0, 0xED,
0xE0, 0xE4, 0xE0, 0x8E, 0x44, 0x18, 0x42, 0x42,
0xE1, 0x2C, 0x0D, 0xF7, 0x30, 0xE2, 0xB8, 0x09,
0x73, 0x50, 0x28, 0xF6, 0x55, 0x85, 0x57, 0x03 },
/* q */
512,
{ 0xC0, 0x81, 0xC4, 0x82, 0x6E, 0xF6, 0x1C, 0x92,
0x83, 0xEC, 0x17, 0xFB, 0x30, 0x98, 0xED, 0x6E,
0x89, 0x92, 0xB2, 0xA1, 0x21, 0x0D, 0xC1, 0x95,
0x49, 0x99, 0xD3, 0x79, 0xD3, 0xBD, 0x94, 0x93,
0xB9, 0x28, 0x68, 0xFF, 0xDE, 0xEB, 0xE8, 0xD2,
0x0B, 0xED, 0x7C, 0x08, 0xD0, 0xD5, 0x59, 0xE3,
0xC1, 0x76, 0xEA, 0xC1, 0xCD, 0xB6, 0x8B, 0x39,
0x4E, 0x29, 0x59, 0x5F, 0xFA, 0xCE, 0x83, 0xA5 },
/* u */
511,
{ 0x4B, 0x87, 0x97, 0x1F, 0x27, 0xED, 0xAA, 0xAF,
0x42, 0xF4, 0x57, 0x82, 0x3F, 0xEC, 0x80, 0xED,
0x1E, 0x91, 0xF8, 0xB4, 0x33, 0xDA, 0xEF, 0xC3,
0x03, 0x53, 0x0F, 0xCE, 0xB9, 0x5F, 0xE4, 0x29,
0xCC, 0xEE, 0x6A, 0x5E, 0x11, 0x0E, 0xFA, 0x66,
0x85, 0xDC, 0xFC, 0x48, 0x31, 0x0C, 0x00, 0x97,
0xC6, 0x0A, 0xF2, 0x34, 0x60, 0x6B, 0xF7, 0x68,
0x09, 0x4E, 0xCF, 0xB1, 0x9E, 0x33, 0x9A, 0x41 },
/* exponent1 */
511,
{ 0x6B, 0x2A, 0x0D, 0xF8, 0x22, 0x7A, 0x71, 0x8C,
0xE2, 0xD5, 0x9D, 0x1C, 0x91, 0xA4, 0x8F, 0x37,
0x0D, 0x5E, 0xF1, 0x26, 0x73, 0x4F, 0x78, 0x3F,
0x82, 0xD8, 0x8B, 0xFE, 0x8F, 0xBD, 0xDB, 0x7D,
0x1F, 0x4C, 0xB1, 0xB9, 0xA8, 0xD7, 0x88, 0x65,
0x3C, 0xC7, 0x24, 0x53, 0x95, 0x1E, 0x20, 0xC3,
0x94, 0x8E, 0x7F, 0x20, 0xCC, 0x2E, 0x88, 0x0E,
0x2F, 0x4A, 0xCB, 0xE3, 0xBD, 0x52, 0x02, 0xFB },
/* exponent2 */
509,
{ 0x10, 0x27, 0xD3, 0xD2, 0x0E, 0x75, 0xE1, 0x17,
0xFA, 0xB2, 0x49, 0xA0, 0xEF, 0x07, 0x26, 0x85,
0xEC, 0x4D, 0xBF, 0x67, 0xFE, 0x5A, 0x25, 0x30,
0xDE, 0x28, 0x66, 0xB3, 0x06, 0xAE, 0x16, 0x55,
0xFF, 0x68, 0x00, 0xC7, 0xD8, 0x71, 0x7B, 0xEC,
0x84, 0xCB, 0xBD, 0x69, 0x0F, 0xFD, 0x97, 0xB9,
0xA1, 0x76, 0xD5, 0x64, 0xC6, 0x5A, 0xD7, 0x7C,
0x4B, 0xAE, 0xF4, 0xAD, 0x35, 0x63, 0x37, 0x71 }
};
static BOOLEAN loadRSAKey( const CRYPT_DEVICE cryptDevice,
CRYPT_CONTEXT *cryptContext,
CRYPT_CONTEXT *decryptContext )
{
CRYPT_PKCINFO_RSA *rsaKey;
const RSA_KEY *rsaKeyTemplate = &rsa1024Key;
const BOOLEAN isDevice = ( cryptDevice != CRYPT_UNUSED ) ? TRUE : FALSE;
int status;
/* Allocate room for the public-key components */
if( ( rsaKey = ( CRYPT_PKCINFO_RSA * ) malloc( sizeof( CRYPT_PKCINFO_RSA ) ) ) == NULL )
return( CRYPT_ERROR_MEMORY );
/* Create the encryption context */
if( cryptContext != NULL )
{
if( isDevice )
status = cryptDeviceCreateContext( cryptDevice, cryptContext,
CRYPT_ALGO_RSA );
else
status = cryptCreateContext( cryptContext, CRYPT_UNUSED,
CRYPT_ALGO_RSA );
if( cryptStatusError( status ) )
{
printf( "crypt%sCreateContext() failed with error code %d.\n",
isDevice ? "Device" : "", status );
return( FALSE );
}
cryptSetAttributeString( *cryptContext, CRYPT_CTXINFO_LABEL,
"RSA public key", strlen( "RSA public key" ) );
cryptInitComponents( rsaKey, CRYPT_KEYTYPE_PUBLIC );
cryptSetComponent( rsaKey->n, rsaKeyTemplate->n, rsaKeyTemplate->nLen );
cryptSetComponent( rsaKey->e, rsaKeyTemplate->e, rsaKeyTemplate->eLen );
status = cryptSetAttributeString( *cryptContext,
CRYPT_CTXINFO_KEY_COMPONENTS, rsaKey,
sizeof( CRYPT_PKCINFO_RSA ) );
cryptDestroyComponents( rsaKey );
if( cryptStatusError( status ) )
{
printf( "Key load failed with error code %d.\n", status );
return( FALSE );
}
if( decryptContext == NULL )
{
/* We're only using a public-key context, return */
free( rsaKey );
return( TRUE );
}
}
/* Create the decryption context */
if( isDevice )
status = cryptDeviceCreateContext( cryptDevice, decryptContext,
CRYPT_ALGO_RSA );
else
status = cryptCreateContext( decryptContext, CRYPT_UNUSED,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -