📄 keyfile.c
字号:
validity += ( 86400 * 32 );
status = cryptSetAttributeString( cryptNewCert,
CRYPT_CERTINFO_VALIDTO, &validity, sizeof( time_t ) );
writtenValidTo = validity;
}
if( cryptStatusOK( status ) )
status = cryptSignCert( cryptNewCert, cryptCAKey );
if( cryptStatusError( status ) )
{
printf( "Encryption cert creation failed with error code %d, "
"line %d.\n", status, __LINE__ );
printErrorAttributeInfo( cryptNewCert );
return( FALSE );
}
cryptDestroyContext( cryptCAKey );
/* First, open the keyset, write the key and certificates (using an
in-memory update), and close it. This tests the ability to use
information cached in memory to handle the update */
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
RENEW_PRIVKEY_FILE, CRYPT_KEYOPT_CREATE );
if( cryptStatusError( status ) )
{
printf( "cryptKeysetOpen() failed with error code %d, line %d.\n",
status, __LINE__ );
return( FALSE );
}
status = cryptAddPrivateKey( cryptKeyset, cryptContext,
TEST_PRIVKEY_PASSWORD );
if( cryptStatusError( status ) )
{
printExtError( cryptKeyset, "cryptAddPrivateKey()", status,
__LINE__ );
return( FALSE );
}
status = cryptAddPublicKey( cryptKeyset, cryptOldCert );
if( cryptStatusOK( status ) )
status = cryptAddPublicKey( cryptKeyset, cryptNewCert );
if( cryptStatusError( status ) )
{
printExtError( cryptKeyset,
"cryptAddPublicKey() (in-memory update)",
status, __LINE__ );
return( FALSE );
}
status = cryptKeysetClose( cryptKeyset );
if( cryptStatusError( status ) )
{
printf( "cryptKeysetClose() failed with error code %d, line %d.\n",
status, __LINE__ );
return( FALSE );
}
/* Then try again, but this time perform an on-disk update, closing the
keyset between the first and second update. This tests the ability
to recover the information needed to handle the update from data in
the keyset */
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
RENEW_PRIVKEY_FILE, CRYPT_KEYOPT_CREATE );
if( cryptStatusOK( status ) )
status = cryptAddPrivateKey( cryptKeyset, cryptContext,
TEST_PRIVKEY_PASSWORD );
if( cryptStatusOK( status ) )
status = cryptAddPublicKey( cryptKeyset, cryptOldCert );
if( cryptStatusOK( status ) )
status = cryptKeysetClose( cryptKeyset );
if( cryptStatusError( status ) )
{
printf( "Keyset creation in preparation for on-disk update failed "
"with error code %d, line %d.\n", status, __LINE__ );
return( FALSE );
}
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
RENEW_PRIVKEY_FILE, CRYPT_KEYOPT_NONE );
if( cryptStatusOK( status ) )
status = cryptAddPublicKey( cryptKeyset, cryptNewCert );
if( cryptStatusError( status ) )
{
printExtError( cryptKeyset, "cryptAddPublicKey() (on-disk update)",
status, __LINE__ );
return( FALSE );
}
status = cryptKeysetClose( cryptKeyset );
if( cryptStatusError( status ) )
{
printf( "cryptKeysetClose() failed with error code %d, line %d.\n",
status, __LINE__ );
return( FALSE );
}
/* Clean up */
cryptDestroyContext( cryptContext );
cryptDestroyCert( cryptOldCert );
cryptDestroyCert( cryptNewCert );
/* Try and read the (newest) key+cert back */
status = getPrivateKey( &cryptContext, RENEW_PRIVKEY_FILE,
RSA_PRIVKEY_LABEL, TEST_PRIVKEY_PASSWORD );
if( cryptStatusError( status ) )
{
printf( "Private key read failed with error code %d, line %d.\n",
status, __LINE__ );
return( FALSE );
}
status = cryptGetAttributeString( cryptContext,
CRYPT_CERTINFO_VALIDTO, &readValidTo, &dummy );
if( cryptStatusError( status ) )
return( attrErrorExit( cryptContext, "cryptGetAttributeString",
status, __LINE__ ) );
if( writtenValidTo != readValidTo )
{
const int diff = ( int ) ( readValidTo - writtenValidTo );
const char *units = ( diff % 60 ) ? "seconds" : "minutes";
printf( "Returned cert != latest valid cert, diff.= %d %s, line "
"%d.\n", ( diff % 60 ) ? diff : diff / 60, units, __LINE__ );
if( diff == 3600 || diff == -3600 )
{
/* See the comment on DST issues in testcert.c */
puts( " (This is probably due to a difference between DST at "
"cert creation and DST\n now, and isn't a serious "
"problem)." );
}
else
return( FALSE );
}
cryptDestroyContext( cryptContext );
puts( "Renewed certificate write to key file succeeded.\n" );
return( TRUE );
}
#else
int testRenewedCertFile( void )
{
/* Since the renewal is time-based, we can't easily test this under
WinCE */
return( TRUE );
}
#endif /* WinCE */
/* Test reading various non-cryptlib PKCS #15 files */
int testReadMiscFile( void )
{
CRYPT_KEYSET cryptKeyset;
/* CRYPT_CONTEXT cryptContext; */
BYTE filenameBuffer[ FILENAME_BUFFER_SIZE ];
#ifdef UNICODE_STRINGS
wchar_t wcBuffer[ FILENAME_BUFFER_SIZE ];
#endif /* UNICODE_STRINGS */
void *fileNamePtr = filenameBuffer;
int status;
puts( "Testing miscellaneous key file read..." );
filenameFromTemplate( filenameBuffer, MISC_PRIVKEY_FILE_TEMPLATE, 1 );
#ifdef UNICODE_STRINGS
mbstowcs( wcBuffer, filenameBuffer, strlen( filenameBuffer ) + 1 );
fileNamePtr = wcBuffer;
#endif /* UNICODE_STRINGS */
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
fileNamePtr, CRYPT_KEYOPT_READONLY );
if( cryptStatusError( status ) )
{
printf( "Couldn't open/scan keyset, status %d, line %d.\n",
status, __LINE__ );
return( FALSE );
}
#if 0
status = cryptGetPrivateKey( cryptKeyset, &cryptContext,
CRYPT_KEYID_NAME,
TEXT( "56303156793b318327b25a84808f2cb311c55b0b" ),
TEXT( "PASSWORD" ) );
if( cryptStatusError( status ) )
{
printExtError( cryptKeyset, "cryptGetPrivateKey()", status,
__LINE__ );
return( FALSE );
}
#endif /* 0 */
cryptKeysetClose( cryptKeyset );
puts( "Renewed certificate write to key file succeeded.\n" );
return( TRUE );
}
/****************************************************************************
* *
* Test Key Generation *
* *
****************************************************************************/
/* The code to generate test CA or other special-purpose certs enables
various special-case extensions such as extKeyUsages or protocol-specific
AIA entries, as well as using a validity period of 5 years instead of the
usual 1 year to avoid problems when users run the self-test on very old
copies of the code. The keys generated are:
File define File Description
----------- ---- -----------
CA_PRIVKEY_FILE key_ca.p15 Root CA key.
Also writes CMP_CA_FILE.
ICA_PRIVKEY_FILE key_ica.p15 Intermediate CA key + root CA cert.
SCEPCA_PRIVKEY_FILE key_sca.p15 SCEP CA key + root CA cert, SCEP CA
keyUsage allows encryption + signing.
Also writes SCEP_CA_FILE.
SERVER_PRIVKEY_FILE key_srv.p15 SSL server key + root CA cert, server
cert has CN = localhost, OCSP AIA.
SSH_PRIVKEY_FILE key_ssh.p15 Raw SSH key.
TSA_PRIVKEY_FILE key_tsa.p15 TSA server key + root CA cert, TSA
cert has TSP extKeyUsage.
USER_PRIVKEY_FILE key_user.p15 User key + root CA cert, user cert
has email address.
(OCSP_CA_FILE is written by the
testCertManagement() code) */
#if 1
/* Create a standalone private key + cert */
static int createCAKeyFile( void )
{
CRYPT_KEYSET cryptKeyset;
CRYPT_CERTIFICATE cryptCert;
CRYPT_CONTEXT cryptContext;
FILE *filePtr;
BYTE certBuffer[ BUFFER_SIZE ];
char filenameBuffer[ FILENAME_BUFFER_SIZE ];
#ifndef _WIN32_WCE /* Windows CE doesn't support ANSI C time functions */
const time_t validity = time( NULL ) + ( 86400L * 365 * 3 );
#endif /* _WIN32_WCE */
int length, status;
/* Create a self-signed CA certificate */
status = cryptCreateContext( &cryptContext, CRYPT_UNUSED, CRYPT_ALGO_RSA );
if( cryptStatusOK( status ) )
status = cryptSetAttributeString( cryptContext, CRYPT_CTXINFO_LABEL,
CA_PRIVKEY_LABEL,
paramStrlen( CA_PRIVKEY_LABEL ) );
if( cryptStatusOK( status ) )
status = cryptGenerateKey( cryptContext );
if( cryptStatusError( status ) )
return( status );
status = cryptCreateCert( &cryptCert, CRYPT_UNUSED,
CRYPT_CERTTYPE_CERTIFICATE );
if( cryptStatusOK( status ) )
status = cryptSetAttribute( cryptCert,
CRYPT_CERTINFO_SUBJECTPUBLICKEYINFO, cryptContext );
if( cryptStatusError( status ) )
return( status );
if( !addCertFields( cryptCert, cACertData, __LINE__ ) )
return( CRYPT_ERROR_FAILED );
#ifndef _WIN32_WCE /* Windows CE doesn't support ANSI C time functions */
/* Make it valid for 5 years instead of 1 to avoid problems when users
run the self-test with very old copies of the code */
cryptSetAttributeString( cryptCert,
CRYPT_CERTINFO_VALIDTO, &validity, sizeof( time_t ) );
if( cryptStatusOK( status ) )
status = cryptSignCert( cryptCert, cryptContext );
if( cryptStatusError( status ) )
return( status );
#endif /* _WIN32_WCE */
/* Open the keyset, update it with the certificate, and close it */
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
CA_PRIVKEY_FILE, CRYPT_KEYOPT_CREATE );
if( cryptStatusError( status ) )
return( status );
status = cryptAddPrivateKey( cryptKeyset, cryptContext,
TEST_PRIVKEY_PASSWORD );
if( cryptStatusOK( status ) )
status = cryptAddPublicKey( cryptKeyset, cryptCert );
if( cryptStatusError( status ) )
return( status );
/* Save the cert to disk for use in request/response protocols */
status = cryptExportCert( certBuffer, BUFFER_SIZE, &length,
CRYPT_CERTFORMAT_CERTIFICATE, cryptCert );
if( cryptStatusError( status ) )
return( status );
filenameFromTemplate( filenameBuffer, CMP_CA_FILE_TEMPLATE, 1 );
if( ( filePtr = fopen( filenameBuffer, "wb" ) ) != NULL )
{
fwrite( certBuffer, length, 1, filePtr );
fclose( filePtr );
}
cryptDestroyCert( cryptCert );
cryptDestroyContext( cryptContext );
cryptKeysetClose( cryptKeyset );
return( CRYPT_OK );
}
/* Create a raw SSH private key */
static int createSSHKeyFile( void )
{
CRYPT_KEYSET cryptKeyset;
CRYPT_CONTEXT cryptContext;
int status;
/* Create a private key */
status = cryptCreateContext( &cryptContext, CRYPT_UNUSED, CRYPT_ALGO_RSA );
if( cryptStatusOK( status ) )
status = cryptSetAttributeString( cryptContext, CRYPT_CTXINFO_LABEL,
USER_PRIVKEY_LABEL,
paramStrlen( USER_PRIVKEY_LABEL ) );
if( cryptStatusOK( status ) )
status = cryptGenerateKey( cryptContext );
if( cryptStatusError( status ) )
return( status );
/* Open the keyset, add the key, and close it */
status = cryptKeysetOpen( &cryptKeyset, CRYPT_UNUSED, CRYPT_KEYSET_FILE,
SSH_PRIVKEY_FILE, CRYPT_KEYOPT_CREATE );
if( cryptStatusError( status ) )
return( status );
status = cryptAddPrivateKey( cryptKeyset, cryptContext,
TEST_PRIVKEY_PASSWORD );
if( cryptStatusError( status ) )
return( status );
cryptDestroyContext( cryptContext );
cryptKeysetClose( cryptKeyset );
return( CRYPT_OK );
}
/* Create a private key + cert + CA cert */
static const CERT_DATA FAR_BSS serverCertRequestData[] = {
/* Identification information */
{ CRYPT_CERTINFO_COUNTRYNAME, IS_STRING, 0, TEXT( "NZ" ) },
{ CRYPT_CERTINFO_ORGANIZATIONNAME, IS_STRING, 0, TEXT( "Dave's Wetaburgers" ) },
{ CRYPT_CERTINFO_ORGANIZATIONALUNITNAME, IS_STRING, 0, TEXT( "Server cert" ) },
{ CRYPT_CERTINFO_COMMONNAME, IS_STRING, 0, TEXT( "localhost" ) },
/* Add an OCSP AIA entry */
{ CRYPT_ATTRIBUTE_CURRENT, IS_NUMERIC, CRYPT_CERTINFO_AUTHORITYINFO_OCSP },
{ CRYPT_CERTINFO_UNIFORMRESOURCEIDENTIFIER, IS_STRING, 0, TEXT( "http://localhost" ) },
{ CRYPT_ATTRIBUTE_NONE, 0, 0, NULL }
};
static const CERT_DATA FAR_BSS iCACertRequestData[] = {
/* Identification information */
{ CRYPT_CERTINFO_COUNTRYNAME, IS_STRING, 0, TEXT( "NZ" ) },
{ CRYPT_CERTINFO_ORGANIZATIONNAME, IS_STRING, 0, TEXT( "Dave's Wetaburgers" ) },
{ CRYPT_CERTINFO_ORGANIZATIONALUNITNAME, IS_STRING, 0, TEXT( "Intermediate CA cert" ) },
{ CRYPT_CERTINFO_COMMONNAME, IS_STRING, 0, TEXT( "Dave's Spare CA" ) },
/* Set the CA key usage extensions */
{ CRYPT_CERTINFO_CA, IS_NUMERIC, TRUE },
{ CRYPT_CERTINFO_KEYUSAGE, IS_NUMERIC, CRYPT_KEYUSAGE_KEYCERTSIGN },
{ CRYPT_ATTRIBUTE_NONE, 0, 0, NULL }
};
static const CERT_DATA FAR_BSS scepCACertRequestData[] = {
/* Identification information */
{ CRYPT_CERTINFO_COUNTRYNAME, IS_STRING, 0, TEXT( "NZ" ) },
{ CRYPT_CERTINFO_ORGANIZATIONNAME, IS_STRING, 0, TEXT( "Dave's Wetaburgers" ) },
{ CRYPT_CERTINFO_ORGANIZATIONALUNITNAME, IS_STRING, 0, TEXT( "SCEP CA cert" ) },
{ CRYPT_CERTINFO_COMMONNAME, IS_STRING, 0, TEXT( "Dave's SCEP CA" ) },
/* Set the CA as well as generic sign+encrypt key usage extensions */
{ CRYPT_CERTINFO_CA, IS_NUMERIC, TRUE },
{ CRYPT_CERTINFO_KEYUSAGE, IS_NUMERIC, CRYPT_KEYUSAGE_KEYCERTSIGN | \
CRYPT_KEYUSAGE_DIGITALSIGNATURE | \
CRYPT_KEYUSAGE_KEYENCIPHERMENT },
{ CRYPT_ATTRIBUTE_NONE, 0, 0, NULL }
};
static const CERT_DATA FAR_BSS tsaCertRequestData[] = {
/* Identification information */
{ CRYPT_CERTINFO_COUNTRYNAME, IS_STRING, 0, TEXT( "NZ" ) },
{ CRYPT_CERTINFO_ORGANIZATIONNAME, IS_STRING, 0, TEXT( "Dave's Wetaburgers" ) },
{ CRYPT_CERTINFO_ORGANIZATIONALUNITNAME, IS_STRING, 0, TEXT( "TSA Cert" ) },
{ CRYPT_CERTINFO_COMMONNAME, IS_STRING, 0, TEXT( "Dave's TSA" ) },
/* Set the TSP extended key usage */
{ CRYPT_CERTINFO_KEYUSAGE, IS_NUMERIC, CRYPT_KEYUSAGE_DIGITALSIGNATURE },
{ CRYPT_CERTINFO_EXTKEY_TIMESTAMPING, IS_NUMERIC, CRYPT_UNUSED },
{ CRYPT_ATTRIBUTE_NONE, 0, 0, NULL }
};
stat
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -