mirror of https://github.com/openssl/openssl.git
				
				
				
			And so it begins... again.
Initial FIPS 140-2 code ported to HEAD. Doesn't even compile yet, may have missing files, extraneous files and other nastiness. In other words: it's experimental ATM, OK?
This commit is contained in:
		
							parent
							
								
									72a267331a
								
							
						
					
					
						commit
						2b4b28dc32
					
				|  | @ -0,0 +1,8 @@ | |||
| lib | ||||
| Makefile.save | ||||
| fips_test_suite | ||||
| fips_premain_dso | ||||
| fips_standalone_sha1 | ||||
| fipscanister.o.sha1 | ||||
| *.flc | ||||
| semantic.cache | ||||
|  | @ -0,0 +1,103 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/evp.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| static struct | ||||
|     { | ||||
|     unsigned char key[16]; | ||||
|     unsigned char plaintext[16]; | ||||
|     unsigned char ciphertext[16]; | ||||
|     } tests[]= | ||||
| 	{ | ||||
| 	{ | ||||
| 	{ 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07, | ||||
| 	  0x08,0x09,0x0A,0x0B,0x0C,0x0D,0x0E,0x0F }, | ||||
| 	{ 0x00,0x11,0x22,0x33,0x44,0x55,0x66,0x77, | ||||
| 	  0x88,0x99,0xAA,0xBB,0xCC,0xDD,0xEE,0xFF }, | ||||
| 	{ 0x69,0xC4,0xE0,0xD8,0x6A,0x7B,0x04,0x30, | ||||
| 	  0xD8,0xCD,0xB7,0x80,0x70,0xB4,0xC5,0x5A }, | ||||
| 	}, | ||||
| 	}; | ||||
| 
 | ||||
| void FIPS_corrupt_aes() | ||||
|     { | ||||
|     tests[0].key[0]++; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_selftest_aes() | ||||
|     { | ||||
|     int n; | ||||
|     int ret = 0; | ||||
|     EVP_CIPHER_CTX ctx; | ||||
|     EVP_CIPHER_CTX_init(&ctx); | ||||
| 
 | ||||
|     for(n=0 ; n < 1 ; ++n) | ||||
| 	{ | ||||
| 	if (fips_cipher_test(&ctx, EVP_aes_128_ecb(), | ||||
| 				tests[n].key, NULL, | ||||
| 				tests[n].plaintext, | ||||
| 				tests[n].ciphertext, | ||||
| 				16) <= 0) | ||||
| 		goto err; | ||||
| 	} | ||||
|     ret = 1; | ||||
|     err: | ||||
|     EVP_CIPHER_CTX_cleanup(&ctx); | ||||
|     if (ret == 0) | ||||
| 	    FIPSerr(FIPS_F_FIPS_SELFTEST_AES,FIPS_R_SELFTEST_FAILED); | ||||
|     return ret; | ||||
|     } | ||||
| #endif | ||||
|  | @ -0,0 +1,939 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2004 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| /*---------------------------------------------
 | ||||
|   NIST AES Algorithm Validation Suite | ||||
|   Test Program | ||||
| 
 | ||||
|   Donated to OpenSSL by: | ||||
|   V-ONE Corporation | ||||
|   20250 Century Blvd, Suite 300 | ||||
|   Germantown, MD 20874 | ||||
|   U.S.A. | ||||
|   ----------------------------------------------*/ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #include <errno.h> | ||||
| #include <assert.h> | ||||
| #include <ctype.h> | ||||
| #include <openssl/aes.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #include <openssl/err.h> | ||||
| #include "e_os.h" | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS AES support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| #define AES_BLOCK_SIZE 16 | ||||
| 
 | ||||
| #define VERBOSE 0 | ||||
| 
 | ||||
| /*-----------------------------------------------*/ | ||||
| 
 | ||||
| static int AESTest(EVP_CIPHER_CTX *ctx, | ||||
| 	    char *amode, int akeysz, unsigned char *aKey,  | ||||
| 	    unsigned char *iVec,  | ||||
| 	    int dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 	    unsigned char *plaintext, unsigned char *ciphertext, int len) | ||||
|     { | ||||
|     const EVP_CIPHER *cipher = NULL; | ||||
| 
 | ||||
|     if (strcasecmp(amode, "CBC") == 0) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_cbc(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_cbc(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_cbc(); | ||||
| 		break; | ||||
| 		} | ||||
| 
 | ||||
| 	} | ||||
|     else if (strcasecmp(amode, "ECB") == 0) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_ecb(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_ecb(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_ecb(); | ||||
| 		break; | ||||
| 		} | ||||
| 	} | ||||
|     else if (strcasecmp(amode, "CFB128") == 0) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_cfb128(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_cfb128(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_cfb128(); | ||||
| 		break; | ||||
| 		} | ||||
| 
 | ||||
| 	} | ||||
|     else if (strncasecmp(amode, "OFB", 3) == 0) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_ofb(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_ofb(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_ofb(); | ||||
| 		break; | ||||
| 		} | ||||
| 	} | ||||
|     else if(!strcasecmp(amode,"CFB1")) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_cfb1(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_cfb1(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_cfb1(); | ||||
| 		break; | ||||
| 		} | ||||
| 	} | ||||
|     else if(!strcasecmp(amode,"CFB8")) | ||||
| 	{ | ||||
| 	switch (akeysz) | ||||
| 		{ | ||||
| 		case 128: | ||||
| 		cipher = EVP_aes_128_cfb8(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 192: | ||||
| 		cipher = EVP_aes_192_cfb8(); | ||||
| 		break; | ||||
| 
 | ||||
| 		case 256: | ||||
| 		cipher = EVP_aes_256_cfb8(); | ||||
| 		break; | ||||
| 		} | ||||
| 	} | ||||
|     else | ||||
| 	{ | ||||
| 	printf("Unknown mode: %s\n", amode); | ||||
| 	return 0; | ||||
| 	} | ||||
|     if (!cipher) | ||||
| 	{ | ||||
| 	printf("Invalid key size: %d\n", akeysz); | ||||
| 	return 0;  | ||||
| 	} | ||||
|     if (EVP_CipherInit_ex(ctx, cipher, NULL, aKey, iVec, dir) <= 0) | ||||
| 	return 0; | ||||
|     if(!strcasecmp(amode,"CFB1")) | ||||
| 	M_EVP_CIPHER_CTX_set_flags(ctx, EVP_CIPH_FLAG_LENGTH_BITS); | ||||
|     if (dir) | ||||
| 		EVP_Cipher(ctx, ciphertext, plaintext, len); | ||||
| 	else | ||||
| 		EVP_Cipher(ctx, plaintext, ciphertext, len); | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /*-----------------------------------------------*/ | ||||
| char *t_tag[2] = {"PLAINTEXT", "CIPHERTEXT"}; | ||||
| char *t_mode[6] = {"CBC","ECB","OFB","CFB1","CFB8","CFB128"}; | ||||
| enum Mode {CBC, ECB, OFB, CFB1, CFB8, CFB128}; | ||||
| enum XCrypt {XDECRYPT, XENCRYPT}; | ||||
| 
 | ||||
| /*=============================*/ | ||||
| /*  Monte Carlo Tests          */ | ||||
| /*-----------------------------*/ | ||||
| 
 | ||||
| /*#define gb(a,b) (((a)[(b)/8] >> ((b)%8))&1)*/ | ||||
| /*#define sb(a,b,v) ((a)[(b)/8]=((a)[(b)/8]&~(1 << ((b)%8)))|(!!(v) << ((b)%8)))*/ | ||||
| 
 | ||||
| #define gb(a,b) (((a)[(b)/8] >> (7-(b)%8))&1) | ||||
| #define sb(a,b,v) ((a)[(b)/8]=((a)[(b)/8]&~(1 << (7-(b)%8)))|(!!(v) << (7-(b)%8))) | ||||
| 
 | ||||
| static int do_mct(char *amode,  | ||||
| 	   int akeysz, unsigned char *aKey,unsigned char *iVec, | ||||
| 	   int dir, unsigned char *text, int len, | ||||
| 	   FILE *rfp) | ||||
|     { | ||||
|     int ret = 0; | ||||
|     unsigned char key[101][32]; | ||||
|     unsigned char iv[101][AES_BLOCK_SIZE]; | ||||
|     unsigned char ptext[1001][32]; | ||||
|     unsigned char ctext[1001][32]; | ||||
|     unsigned char ciphertext[64+4]; | ||||
|     int i, j, n, n1, n2; | ||||
|     int imode = 0, nkeysz = akeysz/8; | ||||
|     EVP_CIPHER_CTX ctx; | ||||
|     EVP_CIPHER_CTX_init(&ctx); | ||||
| 
 | ||||
|     if (len > 32) | ||||
| 	{ | ||||
| 	printf("\n>>>> Length exceeds 32 for %s %d <<<<\n\n",  | ||||
| 	       amode, akeysz); | ||||
| 	return -1; | ||||
| 	} | ||||
|     for (imode = 0; imode < 6; ++imode) | ||||
| 	if (strcmp(amode, t_mode[imode]) == 0) | ||||
| 	    break; | ||||
|     if (imode == 6) | ||||
| 	{  | ||||
| 	printf("Unrecognized mode: %s\n", amode); | ||||
| 	return -1; | ||||
| 	} | ||||
| 
 | ||||
|     memcpy(key[0], aKey, nkeysz); | ||||
|     if (iVec) | ||||
| 	memcpy(iv[0], iVec, AES_BLOCK_SIZE); | ||||
|     if (dir == XENCRYPT) | ||||
| 	memcpy(ptext[0], text, len); | ||||
|     else | ||||
| 	memcpy(ctext[0], text, len); | ||||
|     for (i = 0; i < 100; ++i) | ||||
| 	{ | ||||
| 	/* printf("Iteration %d\n", i); */ | ||||
| 	if (i > 0) | ||||
| 	    { | ||||
| 	    fprintf(rfp,"COUNT = %d\n",i); | ||||
| 	    OutputValue("KEY",key[i],nkeysz,rfp,0); | ||||
| 	    if (imode != ECB)  /* ECB */ | ||||
| 		OutputValue("IV",iv[i],AES_BLOCK_SIZE,rfp,0); | ||||
| 	    /* Output Ciphertext | Plaintext */ | ||||
| 	    OutputValue(t_tag[dir^1],dir ? ptext[0] : ctext[0],len,rfp, | ||||
| 			imode == CFB1); | ||||
| 	    } | ||||
| 	for (j = 0; j < 1000; ++j) | ||||
| 	    { | ||||
| 	    switch (imode) | ||||
| 		{ | ||||
| 	    case ECB: | ||||
| 		if (j == 0) | ||||
| 		    { /* set up encryption */ | ||||
| 		    ret = AESTest(&ctx, amode, akeysz, key[i], NULL,  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  ptext[j], ctext[j], len); | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			memcpy(ptext[j+1], ctext[j], len); | ||||
| 		    else | ||||
| 			memcpy(ctext[j+1], ptext[j], len); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			{ | ||||
| 			EVP_Cipher(&ctx, ctext[j], ptext[j], len); | ||||
| 			memcpy(ptext[j+1], ctext[j], len); | ||||
| 			} | ||||
| 		    else | ||||
| 			{ | ||||
| 			EVP_Cipher(&ctx, ptext[j], ctext[j], len); | ||||
| 			memcpy(ctext[j+1], ptext[j], len); | ||||
| 			} | ||||
| 		    } | ||||
| 		break; | ||||
| 
 | ||||
| 	    case CBC: | ||||
| 	    case OFB:   | ||||
| 	    case CFB128: | ||||
| 		if (j == 0) | ||||
| 		    { | ||||
| 		    ret = AESTest(&ctx, amode, akeysz, key[i], iv[i],  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  ptext[j], ctext[j], len); | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			memcpy(ptext[j+1], iv[i], len); | ||||
| 		    else | ||||
| 			memcpy(ctext[j+1], iv[i], len); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			{ | ||||
| 			EVP_Cipher(&ctx, ctext[j], ptext[j], len); | ||||
| 			memcpy(ptext[j+1], ctext[j-1], len); | ||||
| 			} | ||||
| 		    else | ||||
| 			{ | ||||
| 			EVP_Cipher(&ctx, ptext[j], ctext[j], len); | ||||
| 			memcpy(ctext[j+1], ptext[j-1], len); | ||||
| 			} | ||||
| 		    } | ||||
| 		break; | ||||
| 
 | ||||
| 	    case CFB8: | ||||
| 		if (j == 0) | ||||
| 		    { | ||||
| 		    ret = AESTest(&ctx, amode, akeysz, key[i], iv[i],  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  ptext[j], ctext[j], len); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			EVP_Cipher(&ctx, ctext[j], ptext[j], len); | ||||
| 		    else | ||||
| 			EVP_Cipher(&ctx, ptext[j], ctext[j], len); | ||||
| 		    } | ||||
| 		if (dir == XENCRYPT) | ||||
| 		    { | ||||
| 		    if (j < 16) | ||||
| 			memcpy(ptext[j+1], &iv[i][j], len); | ||||
| 		    else | ||||
| 			memcpy(ptext[j+1], ctext[j-16], len); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if (j < 16) | ||||
| 			memcpy(ctext[j+1], &iv[i][j], len); | ||||
| 		    else | ||||
| 			memcpy(ctext[j+1], ptext[j-16], len); | ||||
| 		    } | ||||
| 		break; | ||||
| 
 | ||||
| 	    case CFB1: | ||||
| 		if(j == 0) | ||||
| 		    { | ||||
| #if 0 | ||||
| 		    /* compensate for wrong endianness of input file */ | ||||
| 		    if(i == 0) | ||||
| 			ptext[0][0]<<=7; | ||||
| #endif | ||||
| 		    ret = AESTest(&ctx,amode,akeysz,key[i],iv[i],dir, | ||||
| 				ptext[j], ctext[j], len); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if (dir == XENCRYPT) | ||||
| 			EVP_Cipher(&ctx, ctext[j], ptext[j], len); | ||||
| 		    else | ||||
| 			EVP_Cipher(&ctx, ptext[j], ctext[j], len); | ||||
| 
 | ||||
| 		    } | ||||
| 		if(dir == XENCRYPT) | ||||
| 		    { | ||||
| 		    if(j < 128) | ||||
| 			sb(ptext[j+1],0,gb(iv[i],j)); | ||||
| 		    else | ||||
| 			sb(ptext[j+1],0,gb(ctext[j-128],0)); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    if(j < 128) | ||||
| 			sb(ctext[j+1],0,gb(iv[i],j)); | ||||
| 		    else | ||||
| 			sb(ctext[j+1],0,gb(ptext[j-128],0)); | ||||
| 		    } | ||||
| 		break; | ||||
| 		} | ||||
| 	    } | ||||
| 	--j; /* reset to last of range */ | ||||
| 	/* Output Ciphertext | Plaintext */ | ||||
| 	OutputValue(t_tag[dir],dir ? ctext[j] : ptext[j],len,rfp, | ||||
| 		    imode == CFB1); | ||||
| 	fprintf(rfp, "\n");  /* add separator */ | ||||
| 
 | ||||
| 	/* Compute next KEY */ | ||||
| 	if (dir == XENCRYPT) | ||||
| 	    { | ||||
| 	    if (imode == CFB8) | ||||
| 		{ /* ct = CT[j-15] || CT[j-14] || ... || CT[j] */ | ||||
| 		for (n1 = 0, n2 = nkeysz-1; n1 < nkeysz; ++n1, --n2) | ||||
| 		    ciphertext[n1] = ctext[j-n2][0]; | ||||
| 		} | ||||
| 	    else if(imode == CFB1) | ||||
| 		{ | ||||
| 		for(n1=0,n2=akeysz-1 ; n1 < akeysz ; ++n1,--n2) | ||||
| 		    sb(ciphertext,n1,gb(ctext[j-n2],0)); | ||||
| 		} | ||||
| 	    else | ||||
| 		switch (akeysz) | ||||
| 		    { | ||||
| 		case 128: | ||||
| 		    memcpy(ciphertext, ctext[j], 16); | ||||
| 		    break; | ||||
| 		case 192: | ||||
| 		    memcpy(ciphertext, ctext[j-1]+8, 8); | ||||
| 		    memcpy(ciphertext+8, ctext[j], 16); | ||||
| 		    break; | ||||
| 		case 256: | ||||
| 		    memcpy(ciphertext, ctext[j-1], 16); | ||||
| 		    memcpy(ciphertext+16, ctext[j], 16); | ||||
| 		    break; | ||||
| 		    } | ||||
| 	    } | ||||
| 	else | ||||
| 	    { | ||||
| 	    if (imode == CFB8) | ||||
| 		{ /* ct = CT[j-15] || CT[j-14] || ... || CT[j] */ | ||||
| 		for (n1 = 0, n2 = nkeysz-1; n1 < nkeysz; ++n1, --n2) | ||||
| 		    ciphertext[n1] = ptext[j-n2][0]; | ||||
| 		} | ||||
| 	    else if(imode == CFB1) | ||||
| 		{ | ||||
| 		for(n1=0,n2=akeysz-1 ; n1 < akeysz ; ++n1,--n2) | ||||
| 		    sb(ciphertext,n1,gb(ptext[j-n2],0)); | ||||
| 		} | ||||
| 	    else | ||||
| 		switch (akeysz) | ||||
| 		    { | ||||
| 		case 128: | ||||
| 		    memcpy(ciphertext, ptext[j], 16); | ||||
| 		    break; | ||||
| 		case 192: | ||||
| 		    memcpy(ciphertext, ptext[j-1]+8, 8); | ||||
| 		    memcpy(ciphertext+8, ptext[j], 16); | ||||
| 		    break; | ||||
| 		case 256: | ||||
| 		    memcpy(ciphertext, ptext[j-1], 16); | ||||
| 		    memcpy(ciphertext+16, ptext[j], 16); | ||||
| 		    break; | ||||
| 		    } | ||||
| 	    } | ||||
| 	/* Compute next key: Key[i+1] = Key[i] xor ct */ | ||||
| 	for (n = 0; n < nkeysz; ++n) | ||||
| 	    key[i+1][n] = key[i][n] ^ ciphertext[n]; | ||||
| 	 | ||||
| 	/* Compute next IV and text */ | ||||
| 	if (dir == XENCRYPT) | ||||
| 	    { | ||||
| 	    switch (imode) | ||||
| 		{ | ||||
| 	    case ECB: | ||||
| 		memcpy(ptext[0], ctext[j], AES_BLOCK_SIZE); | ||||
| 		break; | ||||
| 	    case CBC: | ||||
| 	    case OFB: | ||||
| 	    case CFB128: | ||||
| 		memcpy(iv[i+1], ctext[j], AES_BLOCK_SIZE); | ||||
| 		memcpy(ptext[0], ctext[j-1], AES_BLOCK_SIZE); | ||||
| 		break; | ||||
| 	    case CFB8: | ||||
| 		/* IV[i+1] = ct */ | ||||
| 		for (n1 = 0, n2 = 15; n1 < 16; ++n1, --n2) | ||||
| 		    iv[i+1][n1] = ctext[j-n2][0]; | ||||
| 		ptext[0][0] = ctext[j-16][0]; | ||||
| 		break; | ||||
| 	    case CFB1: | ||||
| 		for(n1=0,n2=127 ; n1 < 128 ; ++n1,--n2) | ||||
| 		    sb(iv[i+1],n1,gb(ctext[j-n2],0)); | ||||
| 		ptext[0][0]=ctext[j-128][0]&0x80; | ||||
| 		break; | ||||
| 		} | ||||
| 	    } | ||||
| 	else | ||||
| 	    { | ||||
| 	    switch (imode) | ||||
| 		{ | ||||
| 	    case ECB: | ||||
| 		memcpy(ctext[0], ptext[j], AES_BLOCK_SIZE); | ||||
| 		break; | ||||
| 	    case CBC: | ||||
| 	    case OFB: | ||||
| 	    case CFB128: | ||||
| 		memcpy(iv[i+1], ptext[j], AES_BLOCK_SIZE); | ||||
| 		memcpy(ctext[0], ptext[j-1], AES_BLOCK_SIZE); | ||||
| 		break; | ||||
| 	    case CFB8: | ||||
| 		for (n1 = 0, n2 = 15; n1 < 16; ++n1, --n2) | ||||
| 		    iv[i+1][n1] = ptext[j-n2][0]; | ||||
| 		ctext[0][0] = ptext[j-16][0]; | ||||
| 		break; | ||||
| 	    case CFB1: | ||||
| 		for(n1=0,n2=127 ; n1 < 128 ; ++n1,--n2) | ||||
| 		    sb(iv[i+1],n1,gb(ptext[j-n2],0)); | ||||
| 		ctext[0][0]=ptext[j-128][0]&0x80; | ||||
| 		break; | ||||
| 		} | ||||
| 	    } | ||||
| 	} | ||||
|      | ||||
|     return ret; | ||||
|     } | ||||
| 
 | ||||
| /*================================================*/ | ||||
| /*----------------------------
 | ||||
|   # Config info for v-one | ||||
|   # AESVS MMT test data for ECB | ||||
|   # State : Encrypt and Decrypt | ||||
|   # Key Length : 256 | ||||
|   # Fri Aug 30 04:07:22 PM | ||||
|   ----------------------------*/ | ||||
| 
 | ||||
| static int proc_file(char *rqfile, char *rspfile) | ||||
|     { | ||||
|     char afn[256], rfn[256]; | ||||
|     FILE *afp = NULL, *rfp = NULL; | ||||
|     char ibuf[2048]; | ||||
|     char tbuf[2048]; | ||||
|     int ilen, len, ret = 0; | ||||
|     char algo[8] = ""; | ||||
|     char amode[8] = ""; | ||||
|     char atest[8] = ""; | ||||
|     int akeysz = 0; | ||||
|     unsigned char iVec[20], aKey[40]; | ||||
|     int dir = -1, err = 0, step = 0; | ||||
|     unsigned char plaintext[2048]; | ||||
|     unsigned char ciphertext[2048]; | ||||
|     char *rp; | ||||
|     EVP_CIPHER_CTX ctx; | ||||
|     EVP_CIPHER_CTX_init(&ctx); | ||||
| 
 | ||||
|     if (!rqfile || !(*rqfile)) | ||||
| 	{ | ||||
| 	printf("No req file\n"); | ||||
| 	return -1; | ||||
| 	} | ||||
|     strcpy(afn, rqfile); | ||||
| 
 | ||||
|     if ((afp = fopen(afn, "r")) == NULL) | ||||
| 	{ | ||||
| 	printf("Cannot open file: %s, %s\n",  | ||||
| 	       afn, strerror(errno)); | ||||
| 	return -1; | ||||
| 	} | ||||
|     if (!rspfile) | ||||
| 	{ | ||||
| 	strcpy(rfn,afn); | ||||
| 	rp=strstr(rfn,"req/"); | ||||
| #ifdef OPENSSL_SYS_WIN32 | ||||
| 	if (!rp) | ||||
| 	    rp=strstr(rfn,"req\\"); | ||||
| #endif | ||||
| 	assert(rp); | ||||
| 	memcpy(rp,"rsp",3); | ||||
| 	rp = strstr(rfn, ".req"); | ||||
| 	memcpy(rp, ".rsp", 4); | ||||
| 	rspfile = rfn; | ||||
| 	} | ||||
|     if ((rfp = fopen(rspfile, "w")) == NULL) | ||||
| 	{ | ||||
| 	printf("Cannot open file: %s, %s\n",  | ||||
| 	       rfn, strerror(errno)); | ||||
| 	fclose(afp); | ||||
| 	afp = NULL; | ||||
| 	return -1; | ||||
| 	} | ||||
|     while (!err && (fgets(ibuf, sizeof(ibuf), afp)) != NULL) | ||||
| 	{ | ||||
| 	tidy_line(tbuf, ibuf); | ||||
| 	ilen = strlen(ibuf); | ||||
| 	/*      printf("step=%d ibuf=%s",step,ibuf); */ | ||||
| 	switch (step) | ||||
| 	    { | ||||
| 	case 0:  /* read preamble */ | ||||
| 	    if (ibuf[0] == '\n') | ||||
| 		{ /* end of preamble */ | ||||
| 		if ((*algo == '\0') || | ||||
| 		    (*amode == '\0') || | ||||
| 		    (akeysz == 0)) | ||||
| 		    { | ||||
| 		    printf("Missing Algorithm, Mode or KeySize (%s/%s/%d)\n", | ||||
| 			   algo,amode,akeysz); | ||||
| 		    err = 1; | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    fputs(ibuf, rfp); | ||||
| 		    ++ step; | ||||
| 		    } | ||||
| 		} | ||||
| 	    else if (ibuf[0] != '#') | ||||
| 		{ | ||||
| 		printf("Invalid preamble item: %s\n", ibuf); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ /* process preamble */ | ||||
| 		char *xp, *pp = ibuf+2; | ||||
| 		int n; | ||||
| 		if (akeysz) | ||||
| 		    { /* insert current time & date */ | ||||
| 		    time_t rtim = time(0); | ||||
| 		    fprintf(rfp, "# %s", ctime(&rtim)); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    fputs(ibuf, rfp); | ||||
| 		    if (strncmp(pp, "AESVS ", 6) == 0) | ||||
| 			{ | ||||
| 			strcpy(algo, "AES"); | ||||
| 			/* get test type */ | ||||
| 			pp += 6; | ||||
| 			xp = strchr(pp, ' '); | ||||
| 			n = xp-pp; | ||||
| 			strncpy(atest, pp, n); | ||||
| 			atest[n] = '\0'; | ||||
| 			/* get mode */ | ||||
| 			xp = strrchr(pp, ' '); /* get mode" */ | ||||
| 			n = strlen(xp+1)-1; | ||||
| 			strncpy(amode, xp+1, n); | ||||
| 			amode[n] = '\0'; | ||||
| 			/* amode[3] = '\0'; */ | ||||
| 			if (VERBOSE) | ||||
| 				printf("Test = %s, Mode = %s\n", atest, amode); | ||||
| 			} | ||||
| 		    else if (strncasecmp(pp, "Key Length : ", 13) == 0) | ||||
| 			{ | ||||
| 			akeysz = atoi(pp+13); | ||||
| 			if (VERBOSE) | ||||
| 				printf("Key size = %d\n", akeysz); | ||||
| 			} | ||||
| 		    } | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 1:  /* [ENCRYPT] | [DECRYPT] */ | ||||
| 	    if (ibuf[0] == '[') | ||||
| 		{ | ||||
| 		fputs(ibuf, rfp); | ||||
| 		++step; | ||||
| 		if (strncasecmp(ibuf, "[ENCRYPT]", 9) == 0) | ||||
| 		    dir = 1; | ||||
| 		else if (strncasecmp(ibuf, "[DECRYPT]", 9) == 0) | ||||
| 		    dir = 0; | ||||
| 		else | ||||
| 		    { | ||||
| 		    printf("Invalid keyword: %s\n", ibuf); | ||||
| 		    err = 1; | ||||
| 		    } | ||||
| 		break; | ||||
| 		} | ||||
| 	    else if (dir == -1) | ||||
| 		{ | ||||
| 		err = 1; | ||||
| 		printf("Missing ENCRYPT/DECRYPT keyword\n"); | ||||
| 		break; | ||||
| 		} | ||||
| 	    else  | ||||
| 		step = 2; | ||||
| 
 | ||||
| 	case 2: /* KEY = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if(*ibuf == '\n') | ||||
| 		break; | ||||
| 	    if(!strncasecmp(ibuf,"COUNT = ",8)) | ||||
| 		break; | ||||
| 
 | ||||
| 	    if (strncasecmp(ibuf, "KEY = ", 6) != 0) | ||||
| 		{ | ||||
| 		printf("Missing KEY\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		len = hex2bin((char*)ibuf+6, aKey); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid KEY\n"); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		PrintValue("KEY", aKey, len); | ||||
| 		if (strcmp(amode, "ECB") == 0) | ||||
| 		    { | ||||
| 		    memset(iVec, 0, sizeof(iVec)); | ||||
| 		    step = (dir)? 4: 5;  /* no ivec for ECB */ | ||||
| 		    } | ||||
| 		else | ||||
| 		    ++step; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 3: /* IV = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "IV = ", 5) != 0) | ||||
| 		{ | ||||
| 		printf("Missing IV\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		len = hex2bin((char*)ibuf+5, iVec); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid IV\n"); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		PrintValue("IV", iVec, len); | ||||
| 		step = (dir)? 4: 5; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 4: /* PLAINTEXT = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "PLAINTEXT = ", 12) != 0) | ||||
| 		{ | ||||
| 		printf("Missing PLAINTEXT\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		int nn = strlen(ibuf+12); | ||||
| 		if(!strcmp(amode,"CFB1")) | ||||
| 		    len=bint2bin(ibuf+12,nn-1,plaintext); | ||||
| 		else | ||||
| 		    len=hex2bin(ibuf+12, plaintext); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid PLAINTEXT: %s", ibuf+12); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		if (len >= (int)sizeof(plaintext)) | ||||
| 		    { | ||||
| 		    printf("Buffer overflow\n"); | ||||
| 		    } | ||||
| 		PrintValue("PLAINTEXT", (unsigned char*)plaintext, len); | ||||
| 		if (strcmp(atest, "MCT") == 0)  /* Monte Carlo Test */ | ||||
| 		    { | ||||
| 		    if(do_mct(amode, akeysz, aKey, iVec,  | ||||
| 			      dir, (unsigned char*)plaintext, len,  | ||||
| 			      rfp) < 0) | ||||
| 			EXIT(1); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    ret = AESTest(&ctx, amode, akeysz, aKey, iVec,  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  plaintext, ciphertext, len); | ||||
| 		    OutputValue("CIPHERTEXT",ciphertext,len,rfp, | ||||
| 				!strcmp(amode,"CFB1")); | ||||
| 		    } | ||||
| 		step = 6; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 5: /* CIPHERTEXT = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "CIPHERTEXT = ", 13) != 0) | ||||
| 		{ | ||||
| 		printf("Missing KEY\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		if(!strcmp(amode,"CFB1")) | ||||
| 		    len=bint2bin(ibuf+13,strlen(ibuf+13)-1,ciphertext); | ||||
| 		else | ||||
| 		    len = hex2bin(ibuf+13,ciphertext); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid CIPHERTEXT\n"); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 
 | ||||
| 		PrintValue("CIPHERTEXT", ciphertext, len); | ||||
| 		if (strcmp(atest, "MCT") == 0)  /* Monte Carlo Test */ | ||||
| 		    { | ||||
| 		    do_mct(amode, akeysz, aKey, iVec,  | ||||
| 			   dir, ciphertext, len, rfp); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    ret = AESTest(&ctx, amode, akeysz, aKey, iVec,  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  plaintext, ciphertext, len); | ||||
| 		    OutputValue("PLAINTEXT",(unsigned char *)plaintext,len,rfp, | ||||
| 				!strcmp(amode,"CFB1")); | ||||
| 		    } | ||||
| 		step = 6; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 6: | ||||
| 	    if (ibuf[0] != '\n') | ||||
| 		{ | ||||
| 		err = 1; | ||||
| 		printf("Missing terminator\n"); | ||||
| 		} | ||||
| 	    else if (strcmp(atest, "MCT") != 0) | ||||
| 		{ /* MCT already added terminating nl */ | ||||
| 		fputs(ibuf, rfp); | ||||
| 		} | ||||
| 	    step = 1; | ||||
| 	    break; | ||||
| 	    } | ||||
| 	} | ||||
|     if (rfp) | ||||
| 	fclose(rfp); | ||||
|     if (afp) | ||||
| 	fclose(afp); | ||||
|     return err; | ||||
|     } | ||||
| 
 | ||||
| /*--------------------------------------------------
 | ||||
|   Processes either a single file or  | ||||
|   a set of files whose names are passed in a file. | ||||
|   A single file is specified as: | ||||
|     aes_test -f xxx.req | ||||
|   A set of files is specified as: | ||||
|     aes_test -d xxxxx.xxx | ||||
|   The default is: -d req.txt | ||||
| --------------------------------------------------*/ | ||||
| int main(int argc, char **argv) | ||||
|     { | ||||
|     char *rqlist = "req.txt", *rspfile = NULL; | ||||
|     FILE *fp = NULL; | ||||
|     char fn[250] = "", rfn[256] = ""; | ||||
|     int f_opt = 0, d_opt = 1; | ||||
|     fips_set_error_print(); | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
|     if(!FIPS_mode_set(1)) | ||||
| 	EXIT(1); | ||||
| #endif | ||||
|     if (argc > 1) | ||||
| 	{ | ||||
| 	if (strcasecmp(argv[1], "-d") == 0) | ||||
| 	    { | ||||
| 	    d_opt = 1; | ||||
| 	    } | ||||
| 	else if (strcasecmp(argv[1], "-f") == 0) | ||||
| 	    { | ||||
| 	    f_opt = 1; | ||||
| 	    d_opt = 0; | ||||
| 	    } | ||||
| 	else | ||||
| 	    { | ||||
| 	    printf("Invalid parameter: %s\n", argv[1]); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 	if (argc < 3) | ||||
| 	    { | ||||
| 	    printf("Missing parameter\n"); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 	if (d_opt) | ||||
| 	    rqlist = argv[2]; | ||||
| 	else | ||||
| 	    { | ||||
| 	    strcpy(fn, argv[2]); | ||||
| 	    rspfile = argv[3]; | ||||
| 	    } | ||||
| 	} | ||||
|     if (d_opt) | ||||
| 	{ /* list of files (directory) */ | ||||
| 	if (!(fp = fopen(rqlist, "r"))) | ||||
| 	    { | ||||
| 	    printf("Cannot open req list file\n"); | ||||
| 	    return -1; | ||||
| 	    } | ||||
| 	while (fgets(fn, sizeof(fn), fp)) | ||||
| 	    { | ||||
| 	    strtok(fn, "\r\n"); | ||||
| 	    strcpy(rfn, fn); | ||||
| 	    if (VERBOSE) | ||||
| 		printf("Processing: %s\n", rfn); | ||||
| 	    if (proc_file(rfn, rspfile)) | ||||
| 		{ | ||||
| 		printf(">>> Processing failed for: %s <<<\n", rfn); | ||||
| 		EXIT(1); | ||||
| 		} | ||||
| 	    } | ||||
| 	fclose(fp); | ||||
| 	} | ||||
|     else /* single file */ | ||||
| 	{ | ||||
| 	if (VERBOSE) | ||||
| 	    printf("Processing: %s\n", fn); | ||||
| 	if (proc_file(fn, rspfile)) | ||||
| 	    { | ||||
| 	    printf(">>> Processing failed for: %s <<<\n", fn); | ||||
| 	    } | ||||
| 	} | ||||
|     EXIT(0); | ||||
|     return 0; | ||||
|     } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,139 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/opensslconf.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| static struct | ||||
|     { | ||||
|     unsigned char key[16]; | ||||
|     unsigned char plaintext[8]; | ||||
|     unsigned char ciphertext[8]; | ||||
|     } tests2[]= | ||||
| 	{ | ||||
| 	{ | ||||
| 	{ 0x7c,0x4f,0x6e,0xf7,0xa2,0x04,0x16,0xec, | ||||
| 	  0x0b,0x6b,0x7c,0x9e,0x5e,0x19,0xa7,0xc4 }, | ||||
| 	{ 0x06,0xa7,0xd8,0x79,0xaa,0xce,0x69,0xef }, | ||||
| 	{ 0x4c,0x11,0x17,0x55,0xbf,0xc4,0x4e,0xfd } | ||||
| 	}, | ||||
| 	{ | ||||
| 	{ 0x5d,0x9e,0x01,0xd3,0x25,0xc7,0x3e,0x34, | ||||
| 	  0x01,0x16,0x7c,0x85,0x23,0xdf,0xe0,0x68 }, | ||||
| 	{ 0x9c,0x50,0x09,0x0f,0x5e,0x7d,0x69,0x7e }, | ||||
| 	{ 0xd2,0x0b,0x18,0xdf,0xd9,0x0d,0x9e,0xff }, | ||||
| 	} | ||||
| 	}; | ||||
| 
 | ||||
| static struct | ||||
|     { | ||||
|     unsigned char key[24]; | ||||
|     unsigned char plaintext[8]; | ||||
|     unsigned char ciphertext[8]; | ||||
|     } tests3[]= | ||||
| 	{ | ||||
| 	{ | ||||
| 	{ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 	  0xFE,0xDC,0xBA,0x98,0x76,0x54,0x32,0x10, | ||||
| 	  0x12,0x34,0x56,0x78,0x9a,0xbc,0xde,0xf0 }, | ||||
| 	{ 0x8f,0x8f,0xbf,0x9b,0x5d,0x48,0xb4,0x1c }, | ||||
| 	{ 0x59,0x8c,0xe5,0xd3,0x6c,0xa2,0xea,0x1b }, | ||||
| 	}, | ||||
| 	{ | ||||
| 	{ 0xDC,0xBA,0x98,0x76,0x54,0x32,0x10,0xFE, | ||||
| 	  0x01,0x23,0x45,0x67,0x89,0xAB,0xCD,0xEF, | ||||
| 	  0xED,0x39,0xD9,0x50,0xFA,0x74,0xBC,0xC4 }, | ||||
| 	{ 0x01,0x23,0x45,0x67,0x89,0xAB,0xCD,0xEF }, | ||||
| 	{ 0x11,0x25,0xb0,0x35,0xbe,0xa0,0x82,0x86 }, | ||||
| 	}, | ||||
| 	}; | ||||
| 
 | ||||
| void FIPS_corrupt_des() | ||||
|     { | ||||
|     tests2[0].plaintext[0]++; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_selftest_des() | ||||
|     { | ||||
|     int n, ret = 0; | ||||
|     EVP_CIPHER_CTX ctx; | ||||
|     EVP_CIPHER_CTX_init(&ctx); | ||||
|     /* Encrypt/decrypt with 2-key 3DES and compare to known answers */ | ||||
|     for(n=0 ; n < 2 ; ++n) | ||||
| 	{ | ||||
| 	if (!fips_cipher_test(&ctx, EVP_des_ede_ecb(), | ||||
| 				tests2[n].key, NULL, | ||||
| 				tests2[n].plaintext, tests2[n].ciphertext, 8)) | ||||
| 		goto err; | ||||
| 	} | ||||
| 
 | ||||
|     /* Encrypt/decrypt with 3DES and compare to known answers */ | ||||
|     for(n=0 ; n < 2 ; ++n) | ||||
| 	{ | ||||
| 	if (!fips_cipher_test(&ctx, EVP_des_ede3_ecb(), | ||||
| 				tests3[n].key, NULL, | ||||
| 				tests3[n].plaintext, tests3[n].ciphertext, 8)) | ||||
| 		goto err; | ||||
| 	} | ||||
|     ret = 1; | ||||
|     err: | ||||
|     EVP_CIPHER_CTX_cleanup(&ctx); | ||||
|     if (ret == 0) | ||||
| 	    FIPSerr(FIPS_F_FIPS_SELFTEST_DES,FIPS_R_SELFTEST_FAILED); | ||||
| 
 | ||||
|     return ret; | ||||
|     } | ||||
| #endif | ||||
|  | @ -0,0 +1,702 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2004 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| /*---------------------------------------------
 | ||||
|   NIST DES Modes of Operation Validation System | ||||
|   Test Program | ||||
| 
 | ||||
|   Based on the AES Validation Suite, which was: | ||||
|   Donated to OpenSSL by: | ||||
|   V-ONE Corporation | ||||
|   20250 Century Blvd, Suite 300 | ||||
|   Germantown, MD 20874 | ||||
|   U.S.A. | ||||
|   ----------------------------------------------*/ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #include <errno.h> | ||||
| #include <assert.h> | ||||
| #include <ctype.h> | ||||
| #include <openssl/des.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #include <openssl/err.h> | ||||
| #include "e_os.h" | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS DES support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| #define DES_BLOCK_SIZE 8 | ||||
| 
 | ||||
| #define VERBOSE 0 | ||||
| 
 | ||||
| static int DESTest(EVP_CIPHER_CTX *ctx, | ||||
| 	    char *amode, int akeysz, unsigned char *aKey,  | ||||
| 	    unsigned char *iVec,  | ||||
| 	    int dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 	    unsigned char *out, unsigned char *in, int len) | ||||
|     { | ||||
|     const EVP_CIPHER *cipher = NULL; | ||||
| 
 | ||||
|     if (akeysz != 192) | ||||
| 	{ | ||||
| 	printf("Invalid key size: %d\n", akeysz); | ||||
| 	EXIT(1); | ||||
| 	} | ||||
| 
 | ||||
|     if (strcasecmp(amode, "CBC") == 0) | ||||
| 	cipher = EVP_des_ede3_cbc(); | ||||
|     else if (strcasecmp(amode, "ECB") == 0) | ||||
| 	cipher = EVP_des_ede3_ecb(); | ||||
|     else if (strcasecmp(amode, "CFB64") == 0) | ||||
| 	cipher = EVP_des_ede3_cfb64(); | ||||
|     else if (strncasecmp(amode, "OFB", 3) == 0) | ||||
| 	cipher = EVP_des_ede3_ofb(); | ||||
|     else if(!strcasecmp(amode,"CFB8")) | ||||
| 	cipher = EVP_des_ede3_cfb8(); | ||||
|     else if(!strcasecmp(amode,"CFB1")) | ||||
| 	cipher = EVP_des_ede3_cfb1(); | ||||
|     else | ||||
| 	{ | ||||
| 	printf("Unknown mode: %s\n", amode); | ||||
| 	EXIT(1); | ||||
| 	} | ||||
| 
 | ||||
|     if (EVP_CipherInit_ex(ctx, cipher, NULL, aKey, iVec, dir) <= 0) | ||||
| 	return 0; | ||||
|     if(!strcasecmp(amode,"CFB1")) | ||||
| 	M_EVP_CIPHER_CTX_set_flags(ctx, EVP_CIPH_FLAG_LENGTH_BITS); | ||||
|     EVP_Cipher(ctx, out, in, len); | ||||
| 
 | ||||
|     return 1; | ||||
|     } | ||||
| #if 0 | ||||
| static void DebugValue(char *tag, unsigned char *val, int len) | ||||
|     { | ||||
|     char obuf[2048]; | ||||
|     int olen; | ||||
|     olen = bin2hex(val, len, obuf); | ||||
|     printf("%s = %.*s\n", tag, olen, obuf); | ||||
|     } | ||||
| #endif | ||||
| static void shiftin(unsigned char *dst,unsigned char *src,int nbits) | ||||
|     { | ||||
|     int n; | ||||
| 
 | ||||
|     /* move the bytes... */ | ||||
|     memmove(dst,dst+nbits/8,3*8-nbits/8); | ||||
|     /* append new data */ | ||||
|     memcpy(dst+3*8-nbits/8,src,(nbits+7)/8); | ||||
|     /* left shift the bits */ | ||||
|     if(nbits%8) | ||||
| 	for(n=0 ; n < 3*8 ; ++n) | ||||
| 	    dst[n]=(dst[n] << (nbits%8))|(dst[n+1] >> (8-nbits%8)); | ||||
|     }	 | ||||
| 
 | ||||
| /*-----------------------------------------------*/ | ||||
| char *t_tag[2] = {"PLAINTEXT", "CIPHERTEXT"}; | ||||
| char *t_mode[6] = {"CBC","ECB","OFB","CFB1","CFB8","CFB64"}; | ||||
| enum Mode {CBC, ECB, OFB, CFB1, CFB8, CFB64}; | ||||
| int Sizes[6]={64,64,64,1,8,64}; | ||||
| 
 | ||||
| static void do_mct(char *amode,  | ||||
| 	    int akeysz, int numkeys, unsigned char *akey,unsigned char *ivec, | ||||
| 	    int dir, unsigned char *text, int len, | ||||
| 	    FILE *rfp) | ||||
|     { | ||||
|     int i,imode; | ||||
|     unsigned char nk[4*8]; /* longest key+8 */ | ||||
|     unsigned char text0[8]; | ||||
| 
 | ||||
|     for (imode=0 ; imode < 6 ; ++imode) | ||||
| 	if(!strcmp(amode,t_mode[imode])) | ||||
| 	    break; | ||||
|     if (imode == 6) | ||||
| 	{  | ||||
| 	printf("Unrecognized mode: %s\n", amode); | ||||
| 	EXIT(1); | ||||
| 	} | ||||
| 
 | ||||
|     for(i=0 ; i < 400 ; ++i) | ||||
| 	{ | ||||
| 	int j; | ||||
| 	int n; | ||||
| 	int kp=akeysz/64; | ||||
| 	unsigned char old_iv[8]; | ||||
| 	EVP_CIPHER_CTX ctx; | ||||
| 	EVP_CIPHER_CTX_init(&ctx); | ||||
| 
 | ||||
| 	fprintf(rfp,"\nCOUNT = %d\n",i); | ||||
| 	if(kp == 1) | ||||
| 	    OutputValue("KEY",akey,8,rfp,0); | ||||
| 	else | ||||
| 	    for(n=0 ; n < kp ; ++n) | ||||
| 		{ | ||||
| 		fprintf(rfp,"KEY%d",n+1); | ||||
| 		OutputValue("",akey+n*8,8,rfp,0); | ||||
| 		} | ||||
| 
 | ||||
| 	if(imode != ECB) | ||||
| 	    OutputValue("IV",ivec,8,rfp,0); | ||||
| 	OutputValue(t_tag[dir^1],text,len,rfp,imode == CFB1); | ||||
| #if 0 | ||||
| 	/* compensate for endianness */ | ||||
| 	if(imode == CFB1) | ||||
| 	    text[0]<<=7; | ||||
| #endif | ||||
| 	memcpy(text0,text,8); | ||||
| 
 | ||||
| 	for(j=0 ; j < 10000 ; ++j) | ||||
| 	    { | ||||
| 	    unsigned char old_text[8]; | ||||
| 
 | ||||
| 	    memcpy(old_text,text,8); | ||||
| 	    if(j == 0) | ||||
| 		{ | ||||
| 		memcpy(old_iv,ivec,8); | ||||
| 		DESTest(&ctx,amode,akeysz,akey,ivec,dir,text,text,len); | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		memcpy(old_iv,ctx.iv,8); | ||||
| 		EVP_Cipher(&ctx,text,text,len); | ||||
| 		} | ||||
| 	    if(j == 9999) | ||||
| 		{ | ||||
| 		OutputValue(t_tag[dir],text,len,rfp,imode == CFB1); | ||||
| 		/*		memcpy(ivec,text,8); */ | ||||
| 		} | ||||
| 	    /*	    DebugValue("iv",ctx.iv,8); */ | ||||
| 	    /* accumulate material for the next key */ | ||||
| 	    shiftin(nk,text,Sizes[imode]); | ||||
| 	    /*	    DebugValue("nk",nk,24);*/ | ||||
| 	    if((dir && (imode == CFB1 || imode == CFB8 || imode == CFB64 | ||||
| 			|| imode == CBC)) || imode == OFB) | ||||
| 		memcpy(text,old_iv,8); | ||||
| 
 | ||||
| 	    if(!dir && (imode == CFB1 || imode == CFB8 || imode == CFB64)) | ||||
| 		{ | ||||
| 		/* the test specifies using the output of the raw DES operation
 | ||||
| 		   which we don't have, so reconstruct it... */ | ||||
| 		for(n=0 ; n < 8 ; ++n) | ||||
| 		    text[n]^=old_text[n]; | ||||
| 		} | ||||
| 	    } | ||||
| 	for(n=0 ; n < 8 ; ++n) | ||||
| 	    akey[n]^=nk[16+n]; | ||||
| 	for(n=0 ; n < 8 ; ++n) | ||||
| 	    akey[8+n]^=nk[8+n]; | ||||
| 	for(n=0 ; n < 8 ; ++n) | ||||
| 	    akey[16+n]^=nk[n]; | ||||
| 	if(numkeys < 3) | ||||
| 	    memcpy(&akey[2*8],akey,8); | ||||
| 	if(numkeys < 2) | ||||
| 	    memcpy(&akey[8],akey,8); | ||||
| 	DES_set_odd_parity((DES_cblock *)akey); | ||||
| 	DES_set_odd_parity((DES_cblock *)(akey+8)); | ||||
| 	DES_set_odd_parity((DES_cblock *)(akey+16)); | ||||
| 	memcpy(ivec,ctx.iv,8); | ||||
| 
 | ||||
| 	/* pointless exercise - the final text doesn't depend on the
 | ||||
| 	   initial text in OFB mode, so who cares what it is? (Who | ||||
| 	   designed these tests?) */ | ||||
| 	if(imode == OFB) | ||||
| 	    for(n=0 ; n < 8 ; ++n) | ||||
| 		text[n]=text0[n]^old_iv[n]; | ||||
| 	} | ||||
|     } | ||||
|      | ||||
| static int proc_file(char *rqfile, char *rspfile) | ||||
|     { | ||||
|     char afn[256], rfn[256]; | ||||
|     FILE *afp = NULL, *rfp = NULL; | ||||
|     char ibuf[2048], tbuf[2048]; | ||||
|     int ilen, len, ret = 0; | ||||
|     char amode[8] = ""; | ||||
|     char atest[100] = ""; | ||||
|     int akeysz=0; | ||||
|     unsigned char iVec[20], aKey[40]; | ||||
|     int dir = -1, err = 0, step = 0; | ||||
|     unsigned char plaintext[2048]; | ||||
|     unsigned char ciphertext[2048]; | ||||
|     char *rp; | ||||
|     EVP_CIPHER_CTX ctx; | ||||
|     int numkeys=1; | ||||
|     EVP_CIPHER_CTX_init(&ctx); | ||||
| 
 | ||||
|     if (!rqfile || !(*rqfile)) | ||||
| 	{ | ||||
| 	printf("No req file\n"); | ||||
| 	return -1; | ||||
| 	} | ||||
|     strcpy(afn, rqfile); | ||||
| 
 | ||||
|     if ((afp = fopen(afn, "r")) == NULL) | ||||
| 	{ | ||||
| 	printf("Cannot open file: %s, %s\n",  | ||||
| 	       afn, strerror(errno)); | ||||
| 	return -1; | ||||
| 	} | ||||
|     if (!rspfile) | ||||
| 	{ | ||||
| 	strcpy(rfn,afn); | ||||
| 	rp=strstr(rfn,"req/"); | ||||
| #ifdef OPENSSL_SYS_WIN32 | ||||
| 	if (!rp) | ||||
| 	    rp=strstr(rfn,"req\\"); | ||||
| #endif | ||||
| 	assert(rp); | ||||
| 	memcpy(rp,"rsp",3); | ||||
| 	rp = strstr(rfn, ".req"); | ||||
| 	memcpy(rp, ".rsp", 4); | ||||
| 	rspfile = rfn; | ||||
| 	} | ||||
|     if ((rfp = fopen(rspfile, "w")) == NULL) | ||||
| 	{ | ||||
| 	printf("Cannot open file: %s, %s\n",  | ||||
| 	       rfn, strerror(errno)); | ||||
| 	fclose(afp); | ||||
| 	afp = NULL; | ||||
| 	return -1; | ||||
| 	} | ||||
|     while (!err && (fgets(ibuf, sizeof(ibuf), afp)) != NULL) | ||||
| 	{ | ||||
| 	tidy_line(tbuf, ibuf); | ||||
| 	ilen = strlen(ibuf); | ||||
| 	/*	printf("step=%d ibuf=%s",step,ibuf);*/ | ||||
| 	if(step == 3 && !strcmp(amode,"ECB")) | ||||
| 	    { | ||||
| 	    memset(iVec, 0, sizeof(iVec)); | ||||
| 	    step = (dir)? 4: 5;  /* no ivec for ECB */ | ||||
| 	    } | ||||
| 	switch (step) | ||||
| 	    { | ||||
| 	case 0:  /* read preamble */ | ||||
| 	    if (ibuf[0] == '\n') | ||||
| 		{ /* end of preamble */ | ||||
| 		if (*amode == '\0') | ||||
| 		    { | ||||
| 		    printf("Missing Mode\n"); | ||||
| 		    err = 1; | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    fputs(ibuf, rfp); | ||||
| 		    ++ step; | ||||
| 		    } | ||||
| 		} | ||||
| 	    else if (ibuf[0] != '#') | ||||
| 		{ | ||||
| 		printf("Invalid preamble item: %s\n", ibuf); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ /* process preamble */ | ||||
| 		char *xp, *pp = ibuf+2; | ||||
| 		int n; | ||||
| 		if(*amode) | ||||
| 		    { /* insert current time & date */ | ||||
| 		    time_t rtim = time(0); | ||||
| 		    fprintf(rfp, "# %s", ctime(&rtim)); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    fputs(ibuf, rfp); | ||||
| 		    if(!strncmp(pp,"INVERSE ",8) || !strncmp(pp,"DES ",4) | ||||
| 		       || !strncmp(pp,"TDES ",5) | ||||
| 		       || !strncmp(pp,"PERMUTATION ",12) | ||||
| 		       || !strncmp(pp,"SUBSTITUTION ",13) | ||||
| 		       || !strncmp(pp,"VARIABLE ",9)) | ||||
| 			{ | ||||
| 			/* get test type */ | ||||
| 			if(!strncmp(pp,"DES ",4)) | ||||
| 			    pp+=4; | ||||
| 			else if(!strncmp(pp,"TDES ",5)) | ||||
| 			    pp+=5; | ||||
| 			xp = strchr(pp, ' '); | ||||
| 			n = xp-pp; | ||||
| 			strncpy(atest, pp, n); | ||||
| 			atest[n] = '\0'; | ||||
| 			/* get mode */ | ||||
| 			xp = strrchr(pp, ' '); /* get mode" */ | ||||
| 			n = strlen(xp+1)-1; | ||||
| 			strncpy(amode, xp+1, n); | ||||
| 			amode[n] = '\0'; | ||||
| 			/* amode[3] = '\0'; */ | ||||
| 			if (VERBOSE) | ||||
| 				printf("Test=%s, Mode=%s\n",atest,amode); | ||||
| 			} | ||||
| 		    } | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 1:  /* [ENCRYPT] | [DECRYPT] */ | ||||
| 	    if(ibuf[0] == '\n') | ||||
| 		break; | ||||
| 	    if (ibuf[0] == '[') | ||||
| 		{ | ||||
| 		fputs(ibuf, rfp); | ||||
| 		++step; | ||||
| 		if (strncasecmp(ibuf, "[ENCRYPT]", 9) == 0) | ||||
| 		    dir = 1; | ||||
| 		else if (strncasecmp(ibuf, "[DECRYPT]", 9) == 0) | ||||
| 		    dir = 0; | ||||
| 		else | ||||
| 		    { | ||||
| 		    printf("Invalid keyword: %s\n", ibuf); | ||||
| 		    err = 1; | ||||
| 		    } | ||||
| 		break; | ||||
| 		} | ||||
| 	    else if (dir == -1) | ||||
| 		{ | ||||
| 		err = 1; | ||||
| 		printf("Missing ENCRYPT/DECRYPT keyword\n"); | ||||
| 		break; | ||||
| 		} | ||||
| 	    else  | ||||
| 		step = 2; | ||||
| 
 | ||||
| 	case 2: /* KEY = xxxx */ | ||||
| 	    if(*ibuf == '\n') | ||||
| 		{ | ||||
| 	        fputs(ibuf, rfp); | ||||
| 		break; | ||||
|                 } | ||||
| 	    if(!strncasecmp(ibuf,"COUNT = ",8)) | ||||
| 		{ | ||||
| 	        fputs(ibuf, rfp); | ||||
| 		break; | ||||
|                 } | ||||
| 	    if(!strncasecmp(ibuf,"COUNT=",6)) | ||||
| 		{ | ||||
| 	        fputs(ibuf, rfp); | ||||
| 		break; | ||||
|                 } | ||||
| 	    if(!strncasecmp(ibuf,"NumKeys = ",10)) | ||||
| 		{ | ||||
| 		numkeys=atoi(ibuf+10); | ||||
| 		break; | ||||
| 		} | ||||
| 	   | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if(!strncasecmp(ibuf,"KEY = ",6)) | ||||
| 		{ | ||||
| 		akeysz=64; | ||||
| 		len = hex2bin((char*)ibuf+6, aKey); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid KEY\n"); | ||||
| 		    err=1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		PrintValue("KEY", aKey, len); | ||||
| 		++step; | ||||
| 		} | ||||
| 	    else if(!strncasecmp(ibuf,"KEYs = ",7)) | ||||
| 		{ | ||||
| 		akeysz=64*3; | ||||
| 		len=hex2bin(ibuf+7,aKey); | ||||
| 		if(len != 8) | ||||
| 		    { | ||||
| 		    printf("Invalid KEY\n"); | ||||
| 		    err=1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		memcpy(aKey+8,aKey,8); | ||||
| 		memcpy(aKey+16,aKey,8); | ||||
| 		ibuf[4]='\0'; | ||||
| 		PrintValue("KEYs",aKey,len); | ||||
| 		++step; | ||||
| 		} | ||||
| 	    else if(!strncasecmp(ibuf,"KEY",3)) | ||||
| 		{ | ||||
| 		int n=ibuf[3]-'1'; | ||||
| 
 | ||||
| 		akeysz=64*3; | ||||
| 		len=hex2bin(ibuf+7,aKey+n*8); | ||||
| 		if(len != 8) | ||||
| 		    { | ||||
| 		    printf("Invalid KEY\n"); | ||||
| 		    err=1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		ibuf[4]='\0'; | ||||
| 		PrintValue(ibuf,aKey,len); | ||||
| 		if(n == 2) | ||||
| 		    ++step; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		printf("Missing KEY\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 3: /* IV = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "IV = ", 5) != 0) | ||||
| 		{ | ||||
| 		printf("Missing IV\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		len = hex2bin((char*)ibuf+5, iVec); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid IV\n"); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		PrintValue("IV", iVec, len); | ||||
| 		step = (dir)? 4: 5; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 4: /* PLAINTEXT = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "PLAINTEXT = ", 12) != 0) | ||||
| 		{ | ||||
| 		printf("Missing PLAINTEXT\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		int nn = strlen(ibuf+12); | ||||
| 		if(!strcmp(amode,"CFB1")) | ||||
| 		    len=bint2bin(ibuf+12,nn-1,plaintext); | ||||
| 		else | ||||
| 		    len=hex2bin(ibuf+12, plaintext); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid PLAINTEXT: %s", ibuf+12); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		if (len >= (int)sizeof(plaintext)) | ||||
| 		    { | ||||
| 		    printf("Buffer overflow\n"); | ||||
| 		    } | ||||
| 		PrintValue("PLAINTEXT", (unsigned char*)plaintext, len); | ||||
| 		if (strcmp(atest, "Monte") == 0)  /* Monte Carlo Test */ | ||||
| 		    { | ||||
| 		    do_mct(amode,akeysz,numkeys,aKey,iVec,dir,plaintext,len,rfp); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    assert(dir == 1); | ||||
| 		    ret = DESTest(&ctx, amode, akeysz, aKey, iVec,  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  ciphertext, plaintext, len); | ||||
| 		    OutputValue("CIPHERTEXT",ciphertext,len,rfp, | ||||
| 				!strcmp(amode,"CFB1")); | ||||
| 		    } | ||||
| 		step = 6; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 5: /* CIPHERTEXT = xxxx */ | ||||
| 	    fputs(ibuf, rfp); | ||||
| 	    if (strncasecmp(ibuf, "CIPHERTEXT = ", 13) != 0) | ||||
| 		{ | ||||
| 		printf("Missing KEY\n"); | ||||
| 		err = 1; | ||||
| 		} | ||||
| 	    else | ||||
| 		{ | ||||
| 		if(!strcmp(amode,"CFB1")) | ||||
| 		    len=bint2bin(ibuf+13,strlen(ibuf+13)-1,ciphertext); | ||||
| 		else | ||||
| 		    len = hex2bin(ibuf+13,ciphertext); | ||||
| 		if (len < 0) | ||||
| 		    { | ||||
| 		    printf("Invalid CIPHERTEXT\n"); | ||||
| 		    err =1; | ||||
| 		    break; | ||||
| 		    } | ||||
| 		 | ||||
| 		PrintValue("CIPHERTEXT", ciphertext, len); | ||||
| 		if (strcmp(atest, "Monte") == 0)  /* Monte Carlo Test */ | ||||
| 		    { | ||||
| 		    do_mct(amode, akeysz, numkeys, aKey, iVec,  | ||||
| 			   dir, ciphertext, len, rfp); | ||||
| 		    } | ||||
| 		else | ||||
| 		    { | ||||
| 		    assert(dir == 0); | ||||
| 		    ret = DESTest(&ctx, amode, akeysz, aKey, iVec,  | ||||
| 				  dir,  /* 0 = decrypt, 1 = encrypt */ | ||||
| 				  plaintext, ciphertext, len); | ||||
| 		    OutputValue("PLAINTEXT",(unsigned char *)plaintext,len,rfp, | ||||
| 				!strcmp(amode,"CFB1")); | ||||
| 		    } | ||||
| 		step = 6; | ||||
| 		} | ||||
| 	    break; | ||||
| 
 | ||||
| 	case 6: | ||||
| 	    if (ibuf[0] != '\n') | ||||
| 		{ | ||||
| 		err = 1; | ||||
| 		printf("Missing terminator\n"); | ||||
| 		} | ||||
| 	    else if (strcmp(atest, "MCT") != 0) | ||||
| 		{ /* MCT already added terminating nl */ | ||||
| 		fputs(ibuf, rfp); | ||||
| 		} | ||||
| 	    step = 1; | ||||
| 	    break; | ||||
| 	    } | ||||
| 	} | ||||
|     if (rfp) | ||||
| 	fclose(rfp); | ||||
|     if (afp) | ||||
| 	fclose(afp); | ||||
|     return err; | ||||
|     } | ||||
| 
 | ||||
| /*--------------------------------------------------
 | ||||
|   Processes either a single file or  | ||||
|   a set of files whose names are passed in a file. | ||||
|   A single file is specified as: | ||||
|     aes_test -f xxx.req | ||||
|   A set of files is specified as: | ||||
|     aes_test -d xxxxx.xxx | ||||
|   The default is: -d req.txt | ||||
| --------------------------------------------------*/ | ||||
| int main(int argc, char **argv) | ||||
|     { | ||||
|     char *rqlist = "req.txt", *rspfile = NULL; | ||||
|     FILE *fp = NULL; | ||||
|     char fn[250] = "", rfn[256] = ""; | ||||
|     int f_opt = 0, d_opt = 1; | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
|     fips_set_error_print(); | ||||
|     if(!FIPS_mode_set(1)) | ||||
| 	EXIT(1); | ||||
| #endif | ||||
|     if (argc > 1) | ||||
| 	{ | ||||
| 	if (strcasecmp(argv[1], "-d") == 0) | ||||
| 	    { | ||||
| 	    d_opt = 1; | ||||
| 	    } | ||||
| 	else if (strcasecmp(argv[1], "-f") == 0) | ||||
| 	    { | ||||
| 	    f_opt = 1; | ||||
| 	    d_opt = 0; | ||||
| 	    } | ||||
| 	else | ||||
| 	    { | ||||
| 	    printf("Invalid parameter: %s\n", argv[1]); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 	if (argc < 3) | ||||
| 	    { | ||||
| 	    printf("Missing parameter\n"); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 	if (d_opt) | ||||
| 	    rqlist = argv[2]; | ||||
| 	else | ||||
| 	    { | ||||
| 	    strcpy(fn, argv[2]); | ||||
| 	    rspfile = argv[3]; | ||||
| 	    } | ||||
| 	} | ||||
|     if (d_opt) | ||||
| 	{ /* list of files (directory) */ | ||||
| 	if (!(fp = fopen(rqlist, "r"))) | ||||
| 	    { | ||||
| 	    printf("Cannot open req list file\n"); | ||||
| 	    return -1; | ||||
| 	    } | ||||
| 	while (fgets(fn, sizeof(fn), fp)) | ||||
| 	    { | ||||
| 	    strtok(fn, "\r\n"); | ||||
| 	    strcpy(rfn, fn); | ||||
| 	    printf("Processing: %s\n", rfn); | ||||
| 	    if (proc_file(rfn, rspfile)) | ||||
| 		{ | ||||
| 		printf(">>> Processing failed for: %s <<<\n", rfn); | ||||
| 		EXIT(1); | ||||
| 		} | ||||
| 	    } | ||||
| 	fclose(fp); | ||||
| 	} | ||||
|     else /* single file */ | ||||
| 	{ | ||||
| 	if (VERBOSE) | ||||
| 		printf("Processing: %s\n", fn); | ||||
| 	if (proc_file(fn, rspfile)) | ||||
| 	    { | ||||
| 	    printf(">>> Processing failed for: %s <<<\n", fn); | ||||
| 	    } | ||||
| 	} | ||||
|     EXIT(0); | ||||
|     return 0; | ||||
|     } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,4 @@ | |||
| lib | ||||
| *.flc | ||||
| semantic.cache | ||||
| Makefile.save | ||||
|  | @ -0,0 +1,115 @@ | |||
| #
 | ||||
| # OpenSSL/fips/dh/Makefile
 | ||||
| #
 | ||||
| 
 | ||||
| DIR=	dh | ||||
| TOP=	../.. | ||||
| CC=	cc | ||||
| INCLUDES= | ||||
| CFLAG=-g | ||||
| INSTALL_PREFIX= | ||||
| OPENSSLDIR=     /usr/local/ssl | ||||
| INSTALLTOP=/usr/local/ssl | ||||
| MAKEDEPPROG=	makedepend | ||||
| MAKEDEPEND=	$(TOP)/util/domd $(TOP) -MD $(MAKEDEPPROG) | ||||
| MAKEFILE=	Makefile | ||||
| AR=		ar r | ||||
| 
 | ||||
| CFLAGS= $(INCLUDES) $(CFLAG) | ||||
| 
 | ||||
| GENERAL=Makefile | ||||
| TEST= | ||||
| APPS= | ||||
| 
 | ||||
| LIB=$(TOP)/libcrypto.a | ||||
| LIBSRC= fips_dh_lib.c | ||||
| LIBOBJ= fips_dh_lib.o | ||||
| 
 | ||||
| SRC= $(LIBSRC) | ||||
| 
 | ||||
| EXHEADER= | ||||
| HEADER=	$(EXHEADER) | ||||
| 
 | ||||
| ALL=    $(GENERAL) $(SRC) $(HEADER) | ||||
| 
 | ||||
| top: | ||||
| 	(cd $(TOP); $(MAKE) DIRS=fips FDIRS=$(DIR) sub_all) | ||||
| 
 | ||||
| all:	lib | ||||
| 
 | ||||
| lib:	$(LIBOBJ) | ||||
| 	@echo $(LIBOBJ) > lib | ||||
| 
 | ||||
| files: | ||||
| 	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO | ||||
| 
 | ||||
| links: | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/include/openssl $(EXHEADER) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/test $(TEST) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/apps $(APPS) | ||||
| 
 | ||||
| install: | ||||
| 	@headerlist="$(EXHEADER)"; for i in $$headerlist; \
 | ||||
| 	do  \
 | ||||
| 	  (cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
 | ||||
| 	  chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
 | ||||
| 	done | ||||
| 
 | ||||
| tags: | ||||
| 	ctags $(SRC) | ||||
| 
 | ||||
| tests: | ||||
| 
 | ||||
| fips_test: | ||||
| 
 | ||||
| lint: | ||||
| 	lint -DLINT $(INCLUDES) $(SRC)>fluff | ||||
| 
 | ||||
| depend: | ||||
| 	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(SRC) $(TEST) | ||||
| 
 | ||||
| dclean: | ||||
| 	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new | ||||
| 	mv -f Makefile.new $(MAKEFILE) | ||||
| 
 | ||||
| clean: | ||||
| 	rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff | ||||
| 
 | ||||
| # DO NOT DELETE THIS LINE -- make depend depends on it.
 | ||||
| 
 | ||||
| fips_dh_check.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dh_check.o: ../../include/openssl/crypto.h ../../include/openssl/dh.h | ||||
| fips_dh_check.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_dh_check.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dh_check.o: ../../include/openssl/opensslconf.h | ||||
| fips_dh_check.o: ../../include/openssl/opensslv.h | ||||
| fips_dh_check.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dh_check.o: ../../include/openssl/safestack.h | ||||
| fips_dh_check.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_dh_check.o: fips_dh_check.c | ||||
| fips_dh_gen.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dh_gen.o: ../../include/openssl/crypto.h ../../include/openssl/dh.h | ||||
| fips_dh_gen.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_dh_gen.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dh_gen.o: ../../include/openssl/opensslconf.h | ||||
| fips_dh_gen.o: ../../include/openssl/opensslv.h | ||||
| fips_dh_gen.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dh_gen.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dh_gen.o: ../../include/openssl/symhacks.h fips_dh_gen.c | ||||
| fips_dh_key.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dh_key.o: ../../include/openssl/crypto.h ../../include/openssl/dh.h | ||||
| fips_dh_key.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_dh_key.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dh_key.o: ../../include/openssl/opensslconf.h | ||||
| fips_dh_key.o: ../../include/openssl/opensslv.h | ||||
| fips_dh_key.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h | ||||
| fips_dh_key.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dh_key.o: ../../include/openssl/symhacks.h fips_dh_key.c | ||||
| fips_dh_lib.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dh_lib.o: ../../include/openssl/crypto.h ../../include/openssl/dh.h | ||||
| fips_dh_lib.o: ../../include/openssl/e_os2.h | ||||
| fips_dh_lib.o: ../../include/openssl/opensslconf.h | ||||
| fips_dh_lib.o: ../../include/openssl/opensslv.h | ||||
| fips_dh_lib.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dh_lib.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dh_lib.o: ../../include/openssl/symhacks.h fips_dh_lib.c | ||||
|  | @ -0,0 +1,95 @@ | |||
| /* fips_dh_lib.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2007. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/dh.h> | ||||
| 
 | ||||
| /* Minimal FIPS versions of FIPS_dh_new() and FIPS_dh_free(): to
 | ||||
|  * reduce external dependencies.  | ||||
|  */ | ||||
| 
 | ||||
| DH *FIPS_dh_new(void) | ||||
| 	{ | ||||
| 	DH *ret; | ||||
| 	ret = OPENSSL_malloc(sizeof(DH)); | ||||
| 	if (!ret) | ||||
| 		return NULL; | ||||
| 	memset(ret, 0, sizeof(DH)); | ||||
| 	ret->meth = DH_OpenSSL(); | ||||
| 	if (ret->meth->init) | ||||
| 		ret->meth->init(ret); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_dh_free(DH *r) | ||||
| 	{ | ||||
| 	if (!r) | ||||
| 		return; | ||||
| 	if (r->meth->finish) | ||||
| 		r->meth->finish(r); | ||||
| 	if (r->p != NULL) BN_clear_free(r->p); | ||||
| 	if (r->g != NULL) BN_clear_free(r->g); | ||||
| 	if (r->q != NULL) BN_clear_free(r->q); | ||||
| 	if (r->j != NULL) BN_clear_free(r->j); | ||||
| 	if (r->seed) OPENSSL_free(r->seed); | ||||
| 	if (r->counter != NULL) BN_clear_free(r->counter); | ||||
| 	if (r->pub_key != NULL) BN_clear_free(r->pub_key); | ||||
| 	if (r->priv_key != NULL) BN_clear_free(r->priv_key); | ||||
| 	OPENSSL_free(r); | ||||
| 	} | ||||
|  | @ -0,0 +1,4 @@ | |||
| lib | ||||
| Makefile.save | ||||
| *.flc | ||||
| semantic.cache | ||||
|  | @ -0,0 +1,191 @@ | |||
| #
 | ||||
| # OpenSSL/fips/dsa/Makefile
 | ||||
| #
 | ||||
| 
 | ||||
| DIR=	dsa | ||||
| TOP=	../.. | ||||
| CC=	cc | ||||
| INCLUDES= | ||||
| CFLAG=-g | ||||
| INSTALL_PREFIX= | ||||
| OPENSSLDIR=     /usr/local/ssl | ||||
| INSTALLTOP=/usr/local/ssl | ||||
| MAKEDEPPROG=	makedepend | ||||
| MAKEDEPEND=	$(TOP)/util/domd $(TOP) -MD $(MAKEDEPPROG) | ||||
| MAKEFILE=	Makefile | ||||
| AR=		ar r | ||||
| 
 | ||||
| CFLAGS= $(INCLUDES) $(CFLAG) | ||||
| 
 | ||||
| GENERAL=Makefile | ||||
| TEST=fips_dsatest.c fips_dssvs.c | ||||
| APPS= | ||||
| 
 | ||||
| LIB=$(TOP)/libcrypto.a | ||||
| LIBSRC= fips_dsa_selftest.c \
 | ||||
| 	fips_dsa_lib.c fips_dsa_sign.c | ||||
| LIBOBJ= fips_dsa_selftest.o \
 | ||||
| 	fips_dsa_lib.o fips_dsa_sign.o | ||||
| 
 | ||||
| SRC= $(LIBSRC) | ||||
| 
 | ||||
| EXHEADER= | ||||
| HEADER=	$(EXHEADER) | ||||
| 
 | ||||
| ALL=    $(GENERAL) $(SRC) $(HEADER) | ||||
| 
 | ||||
| top: | ||||
| 	(cd $(TOP); $(MAKE) DIRS=fips FDIRS=$(DIR) sub_all) | ||||
| 
 | ||||
| all:	lib | ||||
| 
 | ||||
| lib:	$(LIBOBJ) | ||||
| 	@echo $(LIBOBJ) > lib | ||||
| 
 | ||||
| files: | ||||
| 	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO | ||||
| 
 | ||||
| links: | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/include/openssl $(EXHEADER) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/test $(TEST) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/apps $(APPS) | ||||
| 
 | ||||
| install: | ||||
| 	@headerlist="$(EXHEADER)"; for i in $$headerlist; \
 | ||||
| 	do  \
 | ||||
| 	  (cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
 | ||||
| 	  chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
 | ||||
| 	done | ||||
| 
 | ||||
| tags: | ||||
| 	ctags $(SRC) | ||||
| 
 | ||||
| tests: | ||||
| 
 | ||||
| Q=../testvectors/dsa/req | ||||
| A=../testvectors/dsa/rsp | ||||
| 
 | ||||
| fips_test: | ||||
| 	-rm -rf $A | ||||
| 	mkdir $A | ||||
| 	if [ -f $(Q)/PQGGen.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_dssvs pqg < $(Q)/PQGGen.req > $(A)/PQGGen.rsp; fi | ||||
| 	if [ -f $(Q)/KeyPair.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_dssvs keypair < $(Q)/KeyPair.req > $(A)/KeyPair.rsp; fi | ||||
| 	if [ -f $(Q)/SigGen.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_dssvs siggen < $(Q)/SigGen.req > $(A)/SigGen.rsp; fi | ||||
| 	if [ -f $(Q)/SigVer.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_dssvs sigver < $Q/SigVer.req > $A/SigVer.rsp; fi | ||||
| 
 | ||||
| lint: | ||||
| 	lint -DLINT $(INCLUDES) $(SRC)>fluff | ||||
| 
 | ||||
| depend: | ||||
| 	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(SRC) $(TEST) | ||||
| 
 | ||||
| dclean: | ||||
| 	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new | ||||
| 	mv -f Makefile.new $(MAKEFILE) | ||||
| 
 | ||||
| clean: | ||||
| 	rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff | ||||
| # DO NOT DELETE THIS LINE -- make depend depends on it.
 | ||||
| 
 | ||||
| fips_dsa_gen.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dsa_gen.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_dsa_gen.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dsa_gen.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dsa_gen.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dsa_gen.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h | ||||
| fips_dsa_gen.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_gen.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_gen.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h | ||||
| fips_dsa_gen.o: ../../include/openssl/safestack.h ../../include/openssl/sha.h | ||||
| fips_dsa_gen.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_dsa_gen.o: fips_dsa_gen.c | ||||
| fips_dsa_key.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dsa_key.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_dsa_key.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dsa_key.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dsa_key.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dsa_key.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h | ||||
| fips_dsa_key.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_key.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_key.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h | ||||
| fips_dsa_key.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dsa_key.o: ../../include/openssl/symhacks.h ../fips_locl.h fips_dsa_key.c | ||||
| fips_dsa_lib.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dsa_lib.o: ../../include/openssl/crypto.h ../../include/openssl/dsa.h | ||||
| fips_dsa_lib.o: ../../include/openssl/e_os2.h | ||||
| fips_dsa_lib.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_lib.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_lib.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dsa_lib.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dsa_lib.o: ../../include/openssl/symhacks.h fips_dsa_lib.c | ||||
| fips_dsa_ossl.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/bn.h ../../include/openssl/buffer.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/crypto.h ../../include/openssl/dsa.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/e_os2.h ../../include/openssl/ec.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/ecdh.h ../../include/openssl/ecdsa.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/engine.h ../../include/openssl/err.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/evp.h ../../include/openssl/fips.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/lhash.h ../../include/openssl/obj_mac.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/objects.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/ossl_typ.h ../../include/openssl/pkcs7.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/sha.h ../../include/openssl/stack.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/symhacks.h ../../include/openssl/x509.h | ||||
| fips_dsa_ossl.o: ../../include/openssl/x509_vfy.h fips_dsa_ossl.c | ||||
| fips_dsa_selftest.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/obj_mac.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/objects.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/safestack.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/stack.h | ||||
| fips_dsa_selftest.o: ../../include/openssl/symhacks.h fips_dsa_selftest.c | ||||
| fips_dsa_sign.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dsa_sign.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_dsa_sign.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dsa_sign.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dsa_sign.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dsa_sign.o: ../../include/openssl/obj_mac.h | ||||
| fips_dsa_sign.o: ../../include/openssl/objects.h | ||||
| fips_dsa_sign.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsa_sign.o: ../../include/openssl/opensslv.h | ||||
| fips_dsa_sign.o: ../../include/openssl/ossl_typ.h | ||||
| fips_dsa_sign.o: ../../include/openssl/safestack.h ../../include/openssl/sha.h | ||||
| fips_dsa_sign.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_dsa_sign.o: fips_dsa_sign.c | ||||
| fips_dsatest.o: ../../e_os.h ../../include/openssl/asn1.h | ||||
| fips_dsatest.o: ../../include/openssl/bio.h ../../include/openssl/bn.h | ||||
| fips_dsatest.o: ../../include/openssl/buffer.h ../../include/openssl/crypto.h | ||||
| fips_dsatest.o: ../../include/openssl/des.h ../../include/openssl/des_old.h | ||||
| fips_dsatest.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dsatest.o: ../../include/openssl/ec.h ../../include/openssl/ecdh.h | ||||
| fips_dsatest.o: ../../include/openssl/ecdsa.h ../../include/openssl/engine.h | ||||
| fips_dsatest.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dsatest.o: ../../include/openssl/fips.h ../../include/openssl/fips_rand.h | ||||
| fips_dsatest.o: ../../include/openssl/lhash.h ../../include/openssl/obj_mac.h | ||||
| fips_dsatest.o: ../../include/openssl/objects.h | ||||
| fips_dsatest.o: ../../include/openssl/opensslconf.h | ||||
| fips_dsatest.o: ../../include/openssl/opensslv.h | ||||
| fips_dsatest.o: ../../include/openssl/ossl_typ.h ../../include/openssl/pkcs7.h | ||||
| fips_dsatest.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h | ||||
| fips_dsatest.o: ../../include/openssl/sha.h ../../include/openssl/stack.h | ||||
| fips_dsatest.o: ../../include/openssl/symhacks.h ../../include/openssl/ui.h | ||||
| fips_dsatest.o: ../../include/openssl/ui_compat.h ../../include/openssl/x509.h | ||||
| fips_dsatest.o: ../../include/openssl/x509_vfy.h ../fips_utl.h fips_dsatest.c | ||||
| fips_dssvs.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_dssvs.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_dssvs.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_dssvs.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_dssvs.o: ../../include/openssl/fips.h ../../include/openssl/lhash.h | ||||
| fips_dssvs.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h | ||||
| fips_dssvs.o: ../../include/openssl/opensslconf.h | ||||
| fips_dssvs.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h | ||||
| fips_dssvs.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_dssvs.o: ../../include/openssl/symhacks.h ../fips_utl.h fips_dssvs.c | ||||
|  | @ -0,0 +1,95 @@ | |||
| /* fips_dsa_lib.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2007. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| /* Minimal FIPS versions of FIPS_dsa_new() and FIPS_dsa_free: to
 | ||||
|  * reduce external dependencies.  | ||||
|  */ | ||||
| 
 | ||||
| DSA *FIPS_dsa_new(void) | ||||
| 	{ | ||||
| 	DSA *ret; | ||||
| 	ret = OPENSSL_malloc(sizeof(DSA)); | ||||
| 	if (!ret) | ||||
| 		return NULL; | ||||
| 	memset(ret, 0, sizeof(DSA)); | ||||
| 	ret->meth = DSA_OpenSSL(); | ||||
| 	if (ret->meth->init) | ||||
| 		ret->meth->init(ret); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_dsa_free(DSA *r) | ||||
| 	{ | ||||
| 	if (!r) | ||||
| 		return; | ||||
| 	if (r->meth->finish) | ||||
| 		r->meth->finish(r); | ||||
| 	if (r->p != NULL) BN_clear_free(r->p); | ||||
| 	if (r->q != NULL) BN_clear_free(r->q); | ||||
| 	if (r->g != NULL) BN_clear_free(r->g); | ||||
| 	if (r->pub_key != NULL) BN_clear_free(r->pub_key); | ||||
| 	if (r->priv_key != NULL) BN_clear_free(r->priv_key); | ||||
| 	if (r->kinv != NULL) BN_clear_free(r->kinv); | ||||
| 	if (r->r != NULL) BN_clear_free(r->r); | ||||
| 	OPENSSL_free(r); | ||||
| 	} | ||||
| 
 | ||||
|  | @ -0,0 +1,182 @@ | |||
| /* crypto/dsa/dsatest.c */ | ||||
| /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
 | ||||
|  * All rights reserved. | ||||
|  * | ||||
|  * This package is an SSL implementation written | ||||
|  * by Eric Young (eay@cryptsoft.com). | ||||
|  * The implementation was written so as to conform with Netscapes SSL. | ||||
|  *  | ||||
|  * This library is free for commercial and non-commercial use as long as | ||||
|  * the following conditions are aheared to.  The following conditions | ||||
|  * apply to all code found in this distribution, be it the RC4, RSA, | ||||
|  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation | ||||
|  * included with this distribution is covered by the same copyright terms | ||||
|  * except that the holder is Tim Hudson (tjh@cryptsoft.com). | ||||
|  *  | ||||
|  * Copyright remains Eric Young's, and as such any Copyright notices in | ||||
|  * the code are not to be removed. | ||||
|  * If this package is used in a product, Eric Young should be given attribution | ||||
|  * as the author of the parts of the library used. | ||||
|  * This can be in the form of a textual message at program startup or | ||||
|  * in documentation (online or textual) provided with the package. | ||||
|  *  | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * 1. Redistributions of source code must retain the copyright | ||||
|  *    notice, this list of conditions and the following disclaimer. | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in the | ||||
|  *    documentation and/or other materials provided with the distribution. | ||||
|  * 3. All advertising materials mentioning features or use of this software | ||||
|  *    must display the following acknowledgement: | ||||
|  *    "This product includes cryptographic software written by | ||||
|  *     Eric Young (eay@cryptsoft.com)" | ||||
|  *    The word 'cryptographic' can be left out if the rouines from the library | ||||
|  *    being used are not cryptographic related :-). | ||||
|  * 4. If you include any Windows specific code (or a derivative thereof) from  | ||||
|  *    the apps directory (application code) you must include an acknowledgement: | ||||
|  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | ||||
|  *  | ||||
|  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND | ||||
|  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||||
|  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | ||||
|  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||||
|  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||||
|  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||||
|  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||||
|  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||||
|  * SUCH DAMAGE. | ||||
|  *  | ||||
|  * The licence and distribution terms for any publically available version or | ||||
|  * derivative of this code cannot be changed.  i.e. this code cannot simply be | ||||
|  * copied and put under another distribution licence | ||||
|  * [including the GNU Public Licence.] | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/crypto.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| /* seed, out_p, out_q, out_g are taken the NIST test vectors */ | ||||
| 
 | ||||
| static unsigned char seed[20] = { | ||||
| 	0x77, 0x8f, 0x40, 0x74, 0x6f, 0x66, 0xbe, 0x33, 0xce, 0xbe, 0x99, 0x34, | ||||
| 	0x4c, 0xfc, 0xf3, 0x28, 0xaa, 0x70, 0x2d, 0x3a | ||||
|   	}; | ||||
| 
 | ||||
| static unsigned char out_p[] = { | ||||
| 	0xf7, 0x7c, 0x1b, 0x83, 0xd8, 0xe8, 0x5c, 0x7f, 0x85, 0x30, 0x17, 0x57, | ||||
| 	0x21, 0x95, 0xfe, 0x26, 0x04, 0xeb, 0x47, 0x4c, 0x3a, 0x4a, 0x81, 0x4b, | ||||
| 	0x71, 0x2e, 0xed, 0x6e, 0x4f, 0x3d, 0x11, 0x0f, 0x7c, 0xfe, 0x36, 0x43, | ||||
| 	0x51, 0xd9, 0x81, 0x39, 0x17, 0xdf, 0x62, 0xf6, 0x9c, 0x01, 0xa8, 0x69, | ||||
| 	0x71, 0xdd, 0x29, 0x7f, 0x47, 0xe6, 0x65, 0xa6, 0x22, 0xe8, 0x6a, 0x12, | ||||
| 	0x2b, 0xc2, 0x81, 0xff, 0x32, 0x70, 0x2f, 0x9e, 0xca, 0x53, 0x26, 0x47, | ||||
| 	0x0f, 0x59, 0xd7, 0x9e, 0x2c, 0xa5, 0x07, 0xc4, 0x49, 0x52, 0xa3, 0xe4, | ||||
| 	0x6b, 0x04, 0x00, 0x25, 0x49, 0xe2, 0xe6, 0x7f, 0x28, 0x78, 0x97, 0xb8, | ||||
| 	0x3a, 0x32, 0x14, 0x38, 0xa2, 0x51, 0x33, 0x22, 0x44, 0x7e, 0xd7, 0xef, | ||||
| 	0x45, 0xdb, 0x06, 0x4a, 0xd2, 0x82, 0x4a, 0x82, 0x2c, 0xb1, 0xd7, 0xd8, | ||||
| 	0xb6, 0x73, 0x00, 0x4d, 0x94, 0x77, 0x94, 0xef | ||||
| 	}; | ||||
| 
 | ||||
| static unsigned char out_q[] = { | ||||
| 	0xd4, 0x0a, 0xac, 0x9f, 0xbd, 0x8c, 0x80, 0xc2, 0x38, 0x7e, 0x2e, 0x0c, | ||||
| 	0x52, 0x5c, 0xea, 0x34, 0xa1, 0x83, 0x32, 0xf3 | ||||
| 	}; | ||||
| 
 | ||||
| static unsigned char out_g[] = { | ||||
| 	0x34, 0x73, 0x8b, 0x57, 0x84, 0x8e, 0x55, 0xbf, 0x57, 0xcc, 0x41, 0xbb, | ||||
| 	0x5e, 0x2b, 0xd5, 0x42, 0xdd, 0x24, 0x22, 0x2a, 0x09, 0xea, 0x26, 0x1e, | ||||
| 	0x17, 0x65, 0xcb, 0x1a, 0xb3, 0x12, 0x44, 0xa3, 0x9e, 0x99, 0xe9, 0x63, | ||||
| 	0xeb, 0x30, 0xb1, 0x78, 0x7b, 0x09, 0x40, 0x30, 0xfa, 0x83, 0xc2, 0x35, | ||||
| 	0xe1, 0xc4, 0x2d, 0x74, 0x1a, 0xb1, 0x83, 0x54, 0xd8, 0x29, 0xf4, 0xcf, | ||||
| 	0x7f, 0x6f, 0x67, 0x1c, 0x36, 0x49, 0xee, 0x6c, 0xa2, 0x3c, 0x2d, 0x6a, | ||||
| 	0xe9, 0xd3, 0x9a, 0xf6, 0x57, 0x78, 0x6f, 0xfd, 0x33, 0xcd, 0x3c, 0xed, | ||||
| 	0xfd, 0xd4, 0x41, 0xe6, 0x5c, 0x8b, 0xe0, 0x68, 0x31, 0x47, 0x47, 0xaf, | ||||
| 	0x12, 0xa7, 0xf9, 0x32, 0x0d, 0x94, 0x15, 0x48, 0xd0, 0x54, 0x85, 0xb2, | ||||
| 	0x04, 0xb5, 0x4d, 0xd4, 0x9d, 0x05, 0x22, 0x25, 0xd9, 0xfd, 0x6c, 0x36, | ||||
| 	0xef, 0xbe, 0x69, 0x6c, 0x55, 0xf4, 0xee, 0xec | ||||
| 	}; | ||||
| 
 | ||||
| static const unsigned char str1[]="12345678901234567890"; | ||||
| 
 | ||||
| void FIPS_corrupt_dsa() | ||||
|     { | ||||
|     ++seed[0]; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_selftest_dsa() | ||||
|     { | ||||
|     DSA *dsa=NULL; | ||||
|     int counter,i,j, ret = 0; | ||||
|     unsigned char buf[256]; | ||||
|     unsigned long h; | ||||
|     EVP_MD_CTX mctx; | ||||
|     DSA_SIG *dsig = NULL; | ||||
| 
 | ||||
|     EVP_MD_CTX_init(&mctx); | ||||
| 
 | ||||
|     dsa = FIPS_dsa_new(); | ||||
| 
 | ||||
|     if(dsa == NULL) | ||||
| 	goto err; | ||||
|     if(!DSA_generate_parameters_ex(dsa, 1024,seed,20,&counter,&h,NULL)) | ||||
| 	goto err; | ||||
|     if (counter != 378)  | ||||
| 	goto err; | ||||
|     if (h != 2) | ||||
| 	goto err; | ||||
|     i=BN_bn2bin(dsa->q,buf); | ||||
|     j=sizeof(out_q); | ||||
|     if (i != j || memcmp(buf,out_q,i) != 0) | ||||
| 	goto err; | ||||
| 
 | ||||
|     i=BN_bn2bin(dsa->p,buf); | ||||
|     j=sizeof(out_p); | ||||
|     if (i != j || memcmp(buf,out_p,i) != 0) | ||||
| 	goto err; | ||||
| 
 | ||||
|     i=BN_bn2bin(dsa->g,buf); | ||||
|     j=sizeof(out_g); | ||||
|     if (i != j || memcmp(buf,out_g,i) != 0) | ||||
| 	goto err; | ||||
|     DSA_generate_key(dsa); | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto err; | ||||
|     if (!EVP_DigestUpdate(&mctx, str1, 20)) | ||||
| 	goto err; | ||||
|     dsig = FIPS_dsa_sign_ctx(dsa, &mctx); | ||||
|     if (!dsig) | ||||
| 	goto err; | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto err; | ||||
|     if (!EVP_DigestUpdate(&mctx, str1, 20)) | ||||
| 	goto err; | ||||
|     if (FIPS_dsa_verify_ctx(dsa, &mctx, dsig) != 1) | ||||
| 	goto err; | ||||
| 
 | ||||
|     ret = 1; | ||||
| 
 | ||||
|     err: | ||||
|     EVP_MD_CTX_cleanup(&mctx); | ||||
|     if (dsa) | ||||
| 	FIPS_dsa_free(dsa); | ||||
|     if (dsig) | ||||
| 	DSA_SIG_free(dsig); | ||||
|     if (ret == 0) | ||||
| 	    FIPSerr(FIPS_F_FIPS_SELFTEST_DSA,FIPS_R_SELFTEST_FAILED); | ||||
|     return ret; | ||||
|     } | ||||
| #endif | ||||
|  | @ -0,0 +1,96 @@ | |||
| /* fips_dsa_sign.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2007. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/sha.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| /* FIPS versions of DSA_sign() and DSA_verify().
 | ||||
|  * Handle DSA_SIG structures to avoid need to handle ASN1. | ||||
|  */ | ||||
| 
 | ||||
| DSA_SIG * FIPS_dsa_sign_ctx(DSA *dsa, EVP_MD_CTX *ctx) | ||||
| 	{ | ||||
| 	DSA_SIG *s; | ||||
| 	unsigned char dig[EVP_MAX_MD_SIZE]; | ||||
| 	unsigned int dlen; | ||||
|         EVP_DigestFinal_ex(ctx, dig, &dlen); | ||||
| 	s = dsa->meth->dsa_do_sign(dig,dlen,dsa); | ||||
| 	OPENSSL_cleanse(dig, dlen); | ||||
| 	return s; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_dsa_verify_ctx(DSA *dsa, EVP_MD_CTX *ctx, DSA_SIG *s) | ||||
| 	{ | ||||
| 	int ret=-1; | ||||
| 	unsigned char dig[EVP_MAX_MD_SIZE]; | ||||
| 	unsigned int dlen; | ||||
|         EVP_DigestFinal_ex(ctx, dig, &dlen); | ||||
| 	ret=dsa->meth->dsa_do_verify(dig,dlen,s,dsa); | ||||
| 	OPENSSL_cleanse(dig, dlen); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,512 @@ | |||
| #include <openssl/opensslconf.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| #include <stdio.h> | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| { | ||||
|     printf("No FIPS DSA support\n"); | ||||
|     return(0); | ||||
| } | ||||
| #else | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <string.h> | ||||
| #include <ctype.h> | ||||
| 
 | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| static void pbn(const char *name, BIGNUM *bn) | ||||
| 	{ | ||||
| 	int len, i; | ||||
| 	unsigned char *tmp; | ||||
| 	len = BN_num_bytes(bn); | ||||
| 	tmp = OPENSSL_malloc(len); | ||||
| 	if (!tmp) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Memory allocation error\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 	BN_bn2bin(bn, tmp); | ||||
| 	printf("%s = ", name); | ||||
| 	for (i = 0; i < len; i++) | ||||
| 		printf("%02X", tmp[i]); | ||||
| 	fputs("\n", stdout); | ||||
| 	OPENSSL_free(tmp); | ||||
| 	return; | ||||
| 	} | ||||
| 
 | ||||
| static void primes() | ||||
|     { | ||||
|     char buf[10240]; | ||||
|     char lbuf[10240]; | ||||
|     char *keyword, *value; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	fputs(buf,stdout); | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		continue; | ||||
| 	if(!strcmp(keyword,"Prime")) | ||||
| 	    { | ||||
| 	    BIGNUM *pp; | ||||
| 
 | ||||
| 	    pp=BN_new(); | ||||
| 	    do_hex2bn(&pp,value); | ||||
| 	    printf("result= %c\n", | ||||
| 		   BN_is_prime_ex(pp,20,NULL,NULL) ? 'P' : 'F'); | ||||
| 	    }	     | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| int dsa_builtin_paramgen(DSA *ret, size_t bits, size_t qbits, | ||||
| 	const EVP_MD *evpmd, const unsigned char *seed_in, size_t seed_len, | ||||
| 	unsigned char *seed_out, | ||||
| 	int *counter_ret, unsigned long *h_ret, BN_GENCB *cb); | ||||
| 
 | ||||
| static void pqg() | ||||
|     { | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     int nmod=0; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    nmod=atoi(value); | ||||
| 	else if(!strcmp(keyword,"N")) | ||||
| 	    { | ||||
| 	    int n=atoi(value); | ||||
| 
 | ||||
| 	    printf("[mod = %d]\n\n",nmod); | ||||
| 
 | ||||
| 	    while(n--) | ||||
| 		{ | ||||
| 		unsigned char seed[EVP_MAX_MD_SIZE]; | ||||
| 		DSA *dsa; | ||||
| 		int counter; | ||||
| 		unsigned long h; | ||||
| 		dsa = FIPS_dsa_new(); | ||||
| 
 | ||||
| 		if (!dsa_builtin_paramgen(dsa, nmod, 160, NULL, NULL, 0, | ||||
| 					seed,&counter,&h,NULL)) | ||||
| 			exit(1); | ||||
| 		pbn("P",dsa->p); | ||||
| 		pbn("Q",dsa->q); | ||||
| 		pbn("G",dsa->g); | ||||
| 		pv("Seed",seed,20); | ||||
| 		printf("c = %d\n",counter); | ||||
| 		printf("H = %lx\n",h); | ||||
| 		putc('\n',stdout); | ||||
| 		} | ||||
| 	    } | ||||
| 	else | ||||
| 	    fputs(buf,stdout); | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| static void pqgver() | ||||
|     { | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     BIGNUM *p = NULL, *q = NULL, *g = NULL; | ||||
|     int counter, counter2; | ||||
|     unsigned long h, h2; | ||||
|     DSA *dsa=NULL; | ||||
|     int nmod=0; | ||||
|     unsigned char seed[1024]; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	fputs(buf, stdout); | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    nmod=atoi(value); | ||||
| 	else if(!strcmp(keyword,"P")) | ||||
| 	    p=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"Q")) | ||||
| 	    q=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"G")) | ||||
| 	    g=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"Seed")) | ||||
| 	    { | ||||
| 	    int slen = hex2bin(value, seed); | ||||
| 	    if (slen != 20) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Seed parse length error\n"); | ||||
| 		exit (1); | ||||
| 		} | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"c")) | ||||
| 	    counter =atoi(buf+4); | ||||
| 	else if(!strcmp(keyword,"H")) | ||||
| 	    { | ||||
| 	    h = atoi(value); | ||||
| 	    if (!p || !q || !g) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Parse Error\n"); | ||||
| 		exit (1); | ||||
| 		} | ||||
| 	    dsa = FIPS_dsa_new(); | ||||
| 	    if (!DSA_generate_parameters_ex(dsa, nmod,seed,20 ,&counter2,&h2,NULL)) | ||||
| 			exit(1); | ||||
|             if (BN_cmp(dsa->p, p) || BN_cmp(dsa->q, q) || BN_cmp(dsa->g, g) | ||||
| 		|| (counter != counter2) || (h != h2)) | ||||
| 	    	printf("Result = F\n"); | ||||
| 	    else | ||||
| 	    	printf("Result = P\n"); | ||||
| 	    BN_free(p); | ||||
| 	    BN_free(q); | ||||
| 	    BN_free(g); | ||||
| 	    p = NULL; | ||||
| 	    q = NULL; | ||||
| 	    g = NULL; | ||||
| 	    FIPS_dsa_free(dsa); | ||||
| 	    dsa = NULL; | ||||
| 	    } | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| /* Keypair verification routine. NB: this isn't part of the standard FIPS140-2
 | ||||
|  * algorithm tests. It is an additional test to perform sanity checks on the | ||||
|  * output of the KeyPair test. | ||||
|  */ | ||||
| 
 | ||||
| static int dss_paramcheck(int nmod, BIGNUM *p, BIGNUM *q, BIGNUM *g, | ||||
| 							BN_CTX *ctx) | ||||
|     { | ||||
|     BIGNUM *rem = NULL; | ||||
|     if (BN_num_bits(p) != nmod) | ||||
| 	return 0; | ||||
|     if (BN_num_bits(q) != 160) | ||||
| 	return 0; | ||||
|     if (BN_is_prime_ex(p, BN_prime_checks, ctx, NULL) != 1) | ||||
| 	return 0; | ||||
|     if (BN_is_prime_ex(q, BN_prime_checks, ctx, NULL) != 1) | ||||
| 	return 0; | ||||
|     rem = BN_new(); | ||||
|     if (!BN_mod(rem, p, q, ctx) || !BN_is_one(rem) | ||||
|     	|| (BN_cmp(g, BN_value_one()) <= 0) | ||||
| 	|| !BN_mod_exp(rem, g, q, p, ctx) || !BN_is_one(rem)) | ||||
| 	{ | ||||
| 	BN_free(rem); | ||||
| 	return 0; | ||||
| 	} | ||||
|     /* Todo: check g */ | ||||
|     BN_free(rem); | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| static void keyver() | ||||
|     { | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     BIGNUM *p = NULL, *q = NULL, *g = NULL, *X = NULL, *Y = NULL; | ||||
|     BIGNUM *Y2; | ||||
|     BN_CTX *ctx = NULL; | ||||
|     int nmod=0, paramcheck = 0; | ||||
| 
 | ||||
|     ctx = BN_CTX_new(); | ||||
|     Y2 = BN_new(); | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    { | ||||
| 	    if (p) | ||||
| 		BN_free(p); | ||||
| 	    p = NULL; | ||||
| 	    if (q) | ||||
| 		BN_free(q); | ||||
| 	    q = NULL; | ||||
| 	    if (g) | ||||
| 		BN_free(g); | ||||
| 	    g = NULL; | ||||
| 	    paramcheck = 0; | ||||
| 	    nmod=atoi(value); | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"P")) | ||||
| 	    p=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"Q")) | ||||
| 	    q=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"G")) | ||||
| 	    g=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"X")) | ||||
| 	    X=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"Y")) | ||||
| 	    { | ||||
| 	    Y=hex2bn(value); | ||||
| 	    if (!p || !q || !g || !X || !Y) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Parse Error\n"); | ||||
| 		exit (1); | ||||
| 		} | ||||
| 	    pbn("P",p); | ||||
| 	    pbn("Q",q); | ||||
| 	    pbn("G",g); | ||||
| 	    pbn("X",X); | ||||
| 	    pbn("Y",Y); | ||||
| 	    if (!paramcheck) | ||||
| 		{ | ||||
| 		if (dss_paramcheck(nmod, p, q, g, ctx)) | ||||
| 			paramcheck = 1; | ||||
| 		else | ||||
| 			paramcheck = -1; | ||||
| 		} | ||||
| 	    if (paramcheck != 1) | ||||
| 	   	printf("Result = F\n"); | ||||
| 	    else | ||||
| 		{ | ||||
| 		if (!BN_mod_exp(Y2, g, X, p, ctx) || BN_cmp(Y2, Y)) | ||||
| 	    		printf("Result = F\n"); | ||||
| 	        else | ||||
| 	    		printf("Result = P\n"); | ||||
| 		} | ||||
| 	    BN_free(X); | ||||
| 	    BN_free(Y); | ||||
| 	    X = NULL; | ||||
| 	    Y = NULL; | ||||
| 	    } | ||||
| 	} | ||||
| 	if (p) | ||||
| 	    BN_free(p); | ||||
| 	if (q) | ||||
| 	    BN_free(q); | ||||
| 	if (g) | ||||
| 	    BN_free(g); | ||||
| 	if (Y2) | ||||
| 	    BN_free(Y2); | ||||
|     } | ||||
| 
 | ||||
| static void keypair() | ||||
|     { | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     int nmod=0; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    nmod=atoi(value); | ||||
| 	else if(!strcmp(keyword,"N")) | ||||
| 	    { | ||||
| 	    DSA *dsa; | ||||
| 	    int n=atoi(value); | ||||
| 
 | ||||
| 	    printf("[mod = %d]\n\n",nmod); | ||||
| 	    dsa = FIPS_dsa_new(); | ||||
| 	    if (!DSA_generate_parameters_ex(dsa, nmod,NULL,0,NULL,NULL,NULL)) | ||||
| 		exit(1); | ||||
| 	    pbn("P",dsa->p); | ||||
| 	    pbn("Q",dsa->q); | ||||
| 	    pbn("G",dsa->g); | ||||
| 	    putc('\n',stdout); | ||||
| 
 | ||||
| 	    while(n--) | ||||
| 		{ | ||||
| 		if (!DSA_generate_key(dsa)) | ||||
| 			exit(1); | ||||
| 
 | ||||
| 		pbn("X",dsa->priv_key); | ||||
| 		pbn("Y",dsa->pub_key); | ||||
| 		putc('\n',stdout); | ||||
| 		} | ||||
| 	    } | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| static void siggen() | ||||
|     { | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     int nmod=0; | ||||
|     DSA *dsa=NULL; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    { | ||||
| 	    nmod=atoi(value); | ||||
| 	    printf("[mod = %d]\n\n",nmod); | ||||
| 	    if (dsa) | ||||
| 		FIPS_dsa_free(dsa); | ||||
| 	    dsa = FIPS_dsa_new(); | ||||
| 	    if (!DSA_generate_parameters_ex(dsa, nmod,NULL,0,NULL,NULL,NULL)) | ||||
| 		exit(1); | ||||
| 	    pbn("P",dsa->p); | ||||
| 	    pbn("Q",dsa->q); | ||||
| 	    pbn("G",dsa->g); | ||||
| 	    putc('\n',stdout); | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"Msg")) | ||||
| 	    { | ||||
| 	    unsigned char msg[1024]; | ||||
| 	    int n; | ||||
| 	    EVP_MD_CTX mctx; | ||||
| 	    DSA_SIG *sig; | ||||
| 	    EVP_MD_CTX_init(&mctx); | ||||
| 
 | ||||
| 	    n=hex2bin(value,msg); | ||||
| 	    pv("Msg",msg,n); | ||||
| 
 | ||||
| 	    if (!DSA_generate_key(dsa)) | ||||
| 		exit(1); | ||||
| 	    pbn("Y",dsa->pub_key); | ||||
| 
 | ||||
| 	    EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL); | ||||
| 	    EVP_DigestUpdate(&mctx, msg, n); | ||||
| 	    sig = FIPS_dsa_sign_ctx(dsa, &mctx); | ||||
| 
 | ||||
| 	    pbn("R",sig->r); | ||||
| 	    pbn("S",sig->s); | ||||
| 	    putc('\n',stdout); | ||||
| 	    DSA_SIG_free(sig); | ||||
| 	    EVP_MD_CTX_cleanup(&mctx); | ||||
| 	    } | ||||
| 	} | ||||
| 	if (dsa) | ||||
| 		FIPS_dsa_free(dsa); | ||||
|     } | ||||
| 
 | ||||
| static void sigver() | ||||
|     { | ||||
|     DSA *dsa=NULL; | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     unsigned char msg[1024]; | ||||
|     char *keyword, *value; | ||||
|     int nmod=0, n=0; | ||||
|     DSA_SIG sg, *sig = &sg; | ||||
| 
 | ||||
|     sig->r = NULL; | ||||
|     sig->s = NULL; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		{ | ||||
| 		fputs(buf,stdout); | ||||
| 		continue; | ||||
| 		} | ||||
| 	if(!strcmp(keyword,"[mod")) | ||||
| 	    { | ||||
| 	    nmod=atoi(value); | ||||
| 	    if(dsa) | ||||
| 		FIPS_dsa_free(dsa); | ||||
| 	    dsa=FIPS_dsa_new(); | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"P")) | ||||
| 	    dsa->p=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"Q")) | ||||
| 	    dsa->q=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"G")) | ||||
| 	    { | ||||
| 	    dsa->g=hex2bn(value); | ||||
| 
 | ||||
| 	    printf("[mod = %d]\n\n",nmod); | ||||
| 	    pbn("P",dsa->p); | ||||
| 	    pbn("Q",dsa->q); | ||||
| 	    pbn("G",dsa->g); | ||||
| 	    putc('\n',stdout); | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"Msg")) | ||||
| 	    { | ||||
| 	    n=hex2bin(value,msg); | ||||
| 	    pv("Msg",msg,n); | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"Y")) | ||||
| 	    dsa->pub_key=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"R")) | ||||
| 	    sig->r=hex2bn(value); | ||||
| 	else if(!strcmp(keyword,"S")) | ||||
| 	    { | ||||
| 	    EVP_MD_CTX mctx; | ||||
| 	    int r; | ||||
| 	    EVP_MD_CTX_init(&mctx); | ||||
| 	    sig->s=hex2bn(value); | ||||
| 	 | ||||
| 	    pbn("Y",dsa->pub_key); | ||||
| 	    pbn("R",sig->r); | ||||
| 	    pbn("S",sig->s); | ||||
| 	    EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL); | ||||
| 	    EVP_DigestUpdate(&mctx, msg, n); | ||||
| 	    no_err = 1; | ||||
| 	    r = FIPS_dsa_verify_ctx(dsa, &mctx, sig); | ||||
| 	    no_err = 0; | ||||
| 	    EVP_MD_CTX_cleanup(&mctx); | ||||
| 	 | ||||
| 	    printf("Result = %c\n", r == 1 ? 'P' : 'F'); | ||||
| 	    putc('\n',stdout); | ||||
| 	    } | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| int main(int argc,char **argv) | ||||
|     { | ||||
|     if(argc != 2) | ||||
| 	{ | ||||
| 	fprintf(stderr,"%s [prime|pqg|pqgver|keypair|siggen|sigver]\n",argv[0]); | ||||
| 	exit(1); | ||||
| 	} | ||||
|     fips_set_error_print(); | ||||
|     if(!FIPS_mode_set(1)) | ||||
| 	exit(1); | ||||
|     if(!strcmp(argv[1],"prime")) | ||||
| 	primes(); | ||||
|     else if(!strcmp(argv[1],"pqg")) | ||||
| 	pqg(); | ||||
|     else if(!strcmp(argv[1],"pqgver")) | ||||
| 	pqgver(); | ||||
|     else if(!strcmp(argv[1],"keypair")) | ||||
| 	keypair(); | ||||
|     else if(!strcmp(argv[1],"keyver")) | ||||
| 	keyver(); | ||||
|     else if(!strcmp(argv[1],"siggen")) | ||||
| 	siggen(); | ||||
|     else if(!strcmp(argv[1],"sigver")) | ||||
| 	sigver(); | ||||
|     else | ||||
| 	{ | ||||
| 	fprintf(stderr,"Don't know how to %s.\n",argv[1]); | ||||
| 	exit(1); | ||||
| 	} | ||||
| 
 | ||||
|     return 0; | ||||
|     } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,558 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <openssl/rand.h> | ||||
| #include <openssl/fips_rand.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <string.h> | ||||
| #include <limits.h> | ||||
| #include "fips_locl.h" | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| 
 | ||||
| #ifndef PATH_MAX | ||||
| #define PATH_MAX 1024 | ||||
| #endif | ||||
| 
 | ||||
| static int fips_selftest_fail; | ||||
| static int fips_mode; | ||||
| static const void *fips_rand_check; | ||||
| 
 | ||||
| static void fips_set_mode(int onoff) | ||||
| 	{ | ||||
| 	int owning_thread = fips_is_owning_thread(); | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		if (!owning_thread) fips_w_lock(); | ||||
| 		fips_mode = onoff; | ||||
| 		if (!owning_thread) fips_w_unlock(); | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| static void fips_set_rand_check(const void *rand_check) | ||||
| 	{ | ||||
| 	int owning_thread = fips_is_owning_thread(); | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		if (!owning_thread) fips_w_lock(); | ||||
| 		fips_rand_check = rand_check; | ||||
| 		if (!owning_thread) fips_w_unlock(); | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_mode(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	int owning_thread = fips_is_owning_thread(); | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		if (!owning_thread) fips_r_lock(); | ||||
| 		ret = fips_mode; | ||||
| 		if (!owning_thread) fips_r_unlock(); | ||||
| 		} | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| const void *FIPS_rand_check(void) | ||||
| 	{ | ||||
| 	const void *ret = 0; | ||||
| 	int owning_thread = fips_is_owning_thread(); | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		if (!owning_thread) fips_r_lock(); | ||||
| 		ret = fips_rand_check; | ||||
| 		if (!owning_thread) fips_r_unlock(); | ||||
| 		} | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_selftest_failed(void) | ||||
|     { | ||||
|     int ret = 0; | ||||
|     if (fips_is_started()) | ||||
| 	{ | ||||
| 	int owning_thread = fips_is_owning_thread(); | ||||
| 
 | ||||
| 	if (!owning_thread) fips_r_lock(); | ||||
| 	ret = fips_selftest_fail; | ||||
| 	if (!owning_thread) fips_r_unlock(); | ||||
| 	} | ||||
|     return ret; | ||||
|     } | ||||
| 
 | ||||
| /* Selftest failure fatal exit routine. This will be called
 | ||||
|  * during *any* cryptographic operation. It has the minimum | ||||
|  * overhead possible to avoid too big a performance hit. | ||||
|  */ | ||||
| 
 | ||||
| void FIPS_selftest_check(void) | ||||
|     { | ||||
|     if (fips_selftest_fail) | ||||
| 	{ | ||||
| 	OpenSSLDie(__FILE__,__LINE__, "FATAL FIPS SELFTEST FAILURE"); | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| void fips_set_selftest_fail(void) | ||||
|     { | ||||
|     fips_selftest_fail = 1; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_selftest(void) | ||||
|     { | ||||
| 
 | ||||
|     return FIPS_selftest_sha1() | ||||
| 	&& FIPS_selftest_hmac() | ||||
| 	&& FIPS_selftest_aes() | ||||
| 	&& FIPS_selftest_des() | ||||
| 	&& FIPS_selftest_rsa() | ||||
| 	&& FIPS_selftest_dsa(); | ||||
|     } | ||||
| 
 | ||||
| extern const void         *FIPS_text_start(),  *FIPS_text_end(); | ||||
| extern const unsigned char FIPS_rodata_start[], FIPS_rodata_end[]; | ||||
| unsigned char              FIPS_signature [20] = { 0 }; | ||||
| static const char          FIPS_hmac_key[]="etaonrishdlcupfm"; | ||||
| 
 | ||||
| unsigned int FIPS_incore_fingerprint(unsigned char *sig,unsigned int len) | ||||
|     { | ||||
|     const unsigned char *p1 = FIPS_text_start(); | ||||
|     const unsigned char *p2 = FIPS_text_end(); | ||||
|     const unsigned char *p3 = FIPS_rodata_start; | ||||
|     const unsigned char *p4 = FIPS_rodata_end; | ||||
|     HMAC_CTX c; | ||||
| 
 | ||||
|     HMAC_CTX_init(&c); | ||||
|     HMAC_Init(&c,FIPS_hmac_key,strlen(FIPS_hmac_key),EVP_sha1()); | ||||
| 
 | ||||
|     /* detect overlapping regions */ | ||||
|     if (p1<=p3 && p2>=p3) | ||||
| 	p3=p1, p4=p2>p4?p2:p4, p1=NULL, p2=NULL; | ||||
|     else if (p3<=p1 && p4>=p1) | ||||
| 	p3=p3, p4=p2>p4?p2:p4, p1=NULL, p2=NULL; | ||||
| 
 | ||||
|     if (p1) | ||||
| 	HMAC_Update(&c,p1,(size_t)p2-(size_t)p1); | ||||
| 
 | ||||
|     if (FIPS_signature>=p3 && FIPS_signature<p4) | ||||
| 	{ | ||||
| 	/* "punch" hole */ | ||||
| 	HMAC_Update(&c,p3,(size_t)FIPS_signature-(size_t)p3); | ||||
| 	p3 = FIPS_signature+sizeof(FIPS_signature); | ||||
| 	if (p3<p4) | ||||
| 	    HMAC_Update(&c,p3,(size_t)p4-(size_t)p3); | ||||
| 	} | ||||
|     else | ||||
| 	HMAC_Update(&c,p3,(size_t)p4-(size_t)p3); | ||||
| 
 | ||||
|     HMAC_Final(&c,sig,&len); | ||||
|     HMAC_CTX_cleanup(&c); | ||||
| 
 | ||||
|     return len; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_check_incore_fingerprint(void) | ||||
|     { | ||||
|     unsigned char sig[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int len; | ||||
| #if defined(__sgi) && (defined(__mips) || defined(mips)) | ||||
|     extern int __dso_displacement[]; | ||||
| #else | ||||
|     extern int OPENSSL_NONPIC_relocated; | ||||
| #endif | ||||
| 
 | ||||
|     if (FIPS_text_start()==NULL) | ||||
| 	{ | ||||
| 	FIPSerr(FIPS_F_FIPS_CHECK_INCORE_FINGERPRINT,FIPS_R_UNSUPPORTED_PLATFORM); | ||||
| 	return 0; | ||||
| 	} | ||||
| 
 | ||||
|     len=FIPS_incore_fingerprint (sig,sizeof(sig)); | ||||
| 
 | ||||
|     if (len!=sizeof(FIPS_signature) || | ||||
| 	memcmp(FIPS_signature,sig,sizeof(FIPS_signature))) | ||||
| 	{ | ||||
| 	if (FIPS_signature>=FIPS_rodata_start && FIPS_signature<FIPS_rodata_end) | ||||
| 	    FIPSerr(FIPS_F_FIPS_CHECK_INCORE_FINGERPRINT,FIPS_R_FINGERPRINT_DOES_NOT_MATCH_SEGMENT_ALIASING); | ||||
| #if defined(__sgi) && (defined(__mips) || defined(mips)) | ||||
| 	else if (__dso_displacement!=NULL) | ||||
| #else | ||||
| 	else if (OPENSSL_NONPIC_relocated) | ||||
| #endif | ||||
| 	    FIPSerr(FIPS_F_FIPS_CHECK_INCORE_FINGERPRINT,FIPS_R_FINGERPRINT_DOES_NOT_MATCH_NONPIC_RELOCATED); | ||||
| 	else | ||||
| 	    FIPSerr(FIPS_F_FIPS_CHECK_INCORE_FINGERPRINT,FIPS_R_FINGERPRINT_DOES_NOT_MATCH); | ||||
| #ifdef OPENSSL_FIPS_DEBUGGER | ||||
|     	return 1; | ||||
| #else | ||||
| 	return 0; | ||||
| #endif | ||||
| 	} | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| int FIPS_mode_set(int onoff) | ||||
|     { | ||||
|     int fips_set_owning_thread(); | ||||
|     int fips_clear_owning_thread(); | ||||
|     int ret = 0; | ||||
| 
 | ||||
|     fips_w_lock(); | ||||
|     fips_set_started(); | ||||
|     fips_set_owning_thread(); | ||||
| 
 | ||||
|     if(onoff) | ||||
| 	{ | ||||
| 	unsigned char buf[48]; | ||||
| 
 | ||||
| 	fips_selftest_fail = 0; | ||||
| 
 | ||||
| 	/* Don't go into FIPS mode twice, just so we can do automagic
 | ||||
| 	   seeding */ | ||||
| 	if(FIPS_mode()) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_FIPS_MODE_SET,FIPS_R_FIPS_MODE_ALREADY_SET); | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| 
 | ||||
| #ifdef OPENSSL_IA32_SSE2 | ||||
| 	if ((OPENSSL_ia32cap & (1<<25|1<<26)) != (1<<25|1<<26)) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_FIPS_MODE_SET,FIPS_R_UNSUPPORTED_PLATFORM); | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| #endif | ||||
| 
 | ||||
| 	if(fips_signature_witness() != FIPS_signature) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_FIPS_MODE_SET,FIPS_R_CONTRADICTING_EVIDENCE); | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| 
 | ||||
| 	if(!FIPS_check_incore_fingerprint()) | ||||
| 	    { | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| 
 | ||||
| 	/* Perform RNG KAT before seeding */ | ||||
| 	if (!FIPS_selftest_rng()) | ||||
| 	    { | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| 
 | ||||
| 	/* automagically seed PRNG if not already seeded */ | ||||
| 	if(!FIPS_rand_status()) | ||||
| 	    { | ||||
| 	    if(RAND_bytes(buf,sizeof buf) <= 0) | ||||
| 		{ | ||||
| 		fips_selftest_fail = 1; | ||||
| 		ret = 0; | ||||
| 		goto end; | ||||
| 		} | ||||
| 	    FIPS_rand_set_key(buf,32); | ||||
| 	    FIPS_rand_seed(buf+32,16); | ||||
| 	    } | ||||
| 
 | ||||
| 	/* now switch into FIPS mode */ | ||||
| 	fips_set_rand_check(FIPS_rand_method()); | ||||
| 	RAND_set_rand_method(FIPS_rand_method()); | ||||
| 	if(FIPS_selftest()) | ||||
| 	    fips_set_mode(1); | ||||
| 	else | ||||
| 	    { | ||||
| 	    fips_selftest_fail = 1; | ||||
| 	    ret = 0; | ||||
| 	    goto end; | ||||
| 	    } | ||||
| 	ret = 1; | ||||
| 	goto end; | ||||
| 	} | ||||
|     fips_set_mode(0); | ||||
|     fips_selftest_fail = 0; | ||||
|     ret = 1; | ||||
| end: | ||||
|     fips_clear_owning_thread(); | ||||
|     fips_w_unlock(); | ||||
|     return ret; | ||||
|     } | ||||
| 
 | ||||
| void fips_w_lock(void)		{ CRYPTO_w_lock(CRYPTO_LOCK_FIPS); } | ||||
| void fips_w_unlock(void)	{ CRYPTO_w_unlock(CRYPTO_LOCK_FIPS); } | ||||
| void fips_r_lock(void)		{ CRYPTO_r_lock(CRYPTO_LOCK_FIPS); } | ||||
| void fips_r_unlock(void)	{ CRYPTO_r_unlock(CRYPTO_LOCK_FIPS); } | ||||
| 
 | ||||
| static int fips_started = 0; | ||||
| static CRYPTO_THREADID fips_thread; | ||||
| static int fips_thread_set = 0; | ||||
| 
 | ||||
| void fips_set_started(void) | ||||
| 	{ | ||||
| 	fips_started = 1; | ||||
| 	} | ||||
| 
 | ||||
| int fips_is_started(void) | ||||
| 	{ | ||||
| 	return fips_started; | ||||
| 	} | ||||
| 
 | ||||
| int fips_is_owning_thread(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		CRYPTO_r_lock(CRYPTO_LOCK_FIPS2); | ||||
| 		if (fips_thread_set) | ||||
| 			{ | ||||
| 			CRYPTO_THREADID cur; | ||||
| 			CRYPTO_THREADID_current(&cur); | ||||
| 			if (!CRYPTO_THREADID_cmp(&cur, &fips_thread)) | ||||
| 				ret = 1; | ||||
| 			} | ||||
| 		CRYPTO_r_unlock(CRYPTO_LOCK_FIPS2); | ||||
| 		} | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int fips_set_owning_thread(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		CRYPTO_w_lock(CRYPTO_LOCK_FIPS2); | ||||
| 		if (!fips_thread_set) | ||||
| 			{ | ||||
| 			CRYPTO_THREADID_current(&fips_thread); | ||||
| 			ret = 1; | ||||
| 			} | ||||
| 		CRYPTO_w_unlock(CRYPTO_LOCK_FIPS2); | ||||
| 		} | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int fips_clear_owning_thread(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 
 | ||||
| 	if (fips_is_started()) | ||||
| 		{ | ||||
| 		CRYPTO_w_lock(CRYPTO_LOCK_FIPS2); | ||||
| 		if (fips_thread_set) | ||||
| 			{ | ||||
| 			CRYPTO_THREADID cur; | ||||
| 			CRYPTO_THREADID_current(&cur); | ||||
| 			if (!CRYPTO_THREADID_cmp(&cur, &fips_thread)) | ||||
| 				fips_thread_set = 0; | ||||
| 			} | ||||
| 		CRYPTO_w_unlock(CRYPTO_LOCK_FIPS2); | ||||
| 		} | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| unsigned char *fips_signature_witness(void) | ||||
| 	{ | ||||
| 	extern unsigned char FIPS_signature[]; | ||||
| 	return FIPS_signature; | ||||
| 	} | ||||
| 
 | ||||
| /* Generalized public key test routine. Signs and verifies the data
 | ||||
|  * supplied in tbs using mesage digest md and setting RSA padding mode | ||||
|  * pad_mode. If the 'kat' parameter is not NULL it will | ||||
|  * additionally check the signature matches it: a known answer test | ||||
|  * The string "fail_str" is used for identification purposes in case | ||||
|  * of failure. | ||||
|  */ | ||||
| 
 | ||||
| int fips_pkey_signature_test(EVP_PKEY *pkey, | ||||
| 			const unsigned char *tbs, int tbslen, | ||||
| 			const unsigned char *kat, unsigned int katlen, | ||||
| 			const EVP_MD *digest, int pad_mode, | ||||
| 			const char *fail_str) | ||||
| 	{	 | ||||
| 	int ret = 0; | ||||
| 	unsigned char sigtmp[256], *sig = sigtmp; | ||||
| 	unsigned int siglen; | ||||
| 	DSA_SIG *dsig = NULL; | ||||
| 	EVP_MD_CTX mctx; | ||||
| 	EVP_MD_CTX_init(&mctx); | ||||
| 
 | ||||
| 	if ((pkey->type == EVP_PKEY_RSA) | ||||
| 		&& ((size_t)RSA_size(pkey->pkey.rsa) > sizeof(sigtmp))) | ||||
| 		{ | ||||
| 		sig = OPENSSL_malloc(RSA_size(pkey->pkey.rsa)); | ||||
| 		if (!sig) | ||||
| 			{ | ||||
| 			FIPSerr(FIPS_F_FIPS_PKEY_SIGNATURE_TEST,ERR_R_MALLOC_FAILURE); | ||||
| 			return 0; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 	if (tbslen == -1) | ||||
| 		tbslen = strlen((char *)tbs); | ||||
| 
 | ||||
| 	if (!EVP_DigestInit_ex(&mctx, digest, NULL)) | ||||
| 		goto error; | ||||
| 	if (!EVP_DigestUpdate(&mctx, tbs, tbslen)) | ||||
| 		goto error; | ||||
| 	if (pkey->type == EVP_PKEY_RSA) | ||||
| 		{ | ||||
| 		if (!FIPS_rsa_sign_ctx(pkey->pkey.rsa, &mctx, | ||||
| 					pad_mode, 0, NULL, sig, &siglen)) | ||||
| 			goto error; | ||||
| 		} | ||||
| 	else if (pkey->type == EVP_PKEY_DSA) | ||||
| 		{ | ||||
| 		dsig = FIPS_dsa_sign_ctx(pkey->pkey.dsa, &mctx); | ||||
| 		if (!dsig) | ||||
| 			goto error; | ||||
| 		} | ||||
| #if 0 | ||||
| 	else if (!EVP_SignFinal(&mctx, sig, &siglen, pkey)) | ||||
| 		goto error; | ||||
| #endif | ||||
| 
 | ||||
| 	if (kat && ((siglen != katlen) || memcmp(kat, sig, katlen))) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if (!EVP_DigestInit_ex(&mctx, digest, NULL)) | ||||
| 		goto error; | ||||
| 	if (!EVP_DigestUpdate(&mctx, tbs, tbslen)) | ||||
| 		goto error; | ||||
| 	if (pkey->type == EVP_PKEY_RSA) | ||||
| 		{ | ||||
| 		ret = FIPS_rsa_verify_ctx(pkey->pkey.rsa, &mctx, | ||||
| 						pad_mode, 0, NULL, sig, siglen); | ||||
| 		} | ||||
| 	else if (pkey->type == EVP_PKEY_DSA) | ||||
| 		{ | ||||
| 		ret = FIPS_dsa_verify_ctx(pkey->pkey.dsa, &mctx, dsig); | ||||
| 		} | ||||
| #if 0 | ||||
| 	else | ||||
| 		ret = EVP_VerifyFinal(&mctx, sig, siglen, pkey); | ||||
| #endif | ||||
| 
 | ||||
| 	error: | ||||
| 	if (dsig != NULL) | ||||
| 		DSA_SIG_free(dsig); | ||||
| 	if (sig != sigtmp) | ||||
| 		OPENSSL_free(sig); | ||||
| 	EVP_MD_CTX_cleanup(&mctx); | ||||
| 	if (ret != 1) | ||||
| 		{ | ||||
| 		FIPSerr(FIPS_F_FIPS_PKEY_SIGNATURE_TEST,FIPS_R_TEST_FAILURE); | ||||
| 		if (fail_str) | ||||
| 			ERR_add_error_data(2, "Type=", fail_str); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| /* Generalized symmetric cipher test routine. Encrypt data, verify result
 | ||||
|  * against known answer, decrypt and compare with original plaintext. | ||||
|  */ | ||||
| 
 | ||||
| int fips_cipher_test(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher, | ||||
| 			const unsigned char *key, | ||||
| 			const unsigned char *iv, | ||||
| 			const unsigned char *plaintext, | ||||
| 			const unsigned char *ciphertext, | ||||
| 			int len) | ||||
| 	{ | ||||
| 	unsigned char pltmp[FIPS_MAX_CIPHER_TEST_SIZE]; | ||||
| 	unsigned char citmp[FIPS_MAX_CIPHER_TEST_SIZE]; | ||||
| 	OPENSSL_assert(len <= FIPS_MAX_CIPHER_TEST_SIZE); | ||||
| 	if (EVP_CipherInit_ex(ctx, cipher, NULL, key, iv, 1) <= 0) | ||||
| 		return 0; | ||||
| 	EVP_Cipher(ctx, citmp, plaintext, len); | ||||
| 	if (memcmp(citmp, ciphertext, len)) | ||||
| 		return 0; | ||||
| 	if (EVP_CipherInit_ex(ctx, cipher, NULL, key, iv, 0) <= 0) | ||||
| 		return 0; | ||||
| 	EVP_Cipher(ctx, pltmp, citmp, len); | ||||
| 	if (memcmp(pltmp, plaintext, len)) | ||||
| 		return 0; | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| #if 0 | ||||
| /* The purpose of this is to ensure the error code exists and the function
 | ||||
|  * name is to keep the error checking script quiet | ||||
|  */ | ||||
| void hash_final(void) | ||||
| 	{ | ||||
| 	FIPSerr(FIPS_F_HASH_FINAL,FIPS_R_NON_FIPS_METHOD); | ||||
| 	} | ||||
| #endif | ||||
| 
 | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,192 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <openssl/opensslconf.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| #error FIPS is disabled. | ||||
| #endif | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| extern "C" { | ||||
| #endif | ||||
| 
 | ||||
| struct dsa_st; | ||||
| struct evp_pkey_st; | ||||
| struct env_md_st; | ||||
| struct evp_cipher_st; | ||||
| struct evp_cipher_ctx_st; | ||||
| 
 | ||||
| int FIPS_mode_set(int onoff); | ||||
| int FIPS_mode(void); | ||||
| const void *FIPS_rand_check(void); | ||||
| int FIPS_selftest(void); | ||||
| int FIPS_selftest_failed(void); | ||||
| void FIPS_selftest_check(void); | ||||
| void FIPS_corrupt_sha1(void); | ||||
| int FIPS_selftest_sha1(void); | ||||
| void FIPS_corrupt_aes(void); | ||||
| int FIPS_selftest_aes(void); | ||||
| void FIPS_corrupt_des(void); | ||||
| int FIPS_selftest_des(void); | ||||
| void FIPS_corrupt_rsa(void); | ||||
| void FIPS_corrupt_rsa_keygen(void); | ||||
| int FIPS_selftest_rsa(void); | ||||
| void FIPS_corrupt_dsa(void); | ||||
| void FIPS_corrupt_dsa_keygen(void); | ||||
| int FIPS_selftest_dsa(void); | ||||
| void FIPS_corrupt_rng(void); | ||||
| void FIPS_rng_stick(void); | ||||
| int FIPS_selftest_rng(void); | ||||
| int FIPS_selftest_hmac(void); | ||||
| 
 | ||||
| unsigned int FIPS_incore_fingerprint(unsigned char *sig,unsigned int len); | ||||
| int FIPS_check_incore_fingerprint(void); | ||||
| 
 | ||||
| int fips_pkey_signature_test(struct evp_pkey_st *pkey, | ||||
| 			const unsigned char *tbs, int tbslen, | ||||
| 			const unsigned char *kat, unsigned int katlen, | ||||
| 			const struct env_md_st *digest, int pad_mode, | ||||
| 			const char *fail_str); | ||||
| 
 | ||||
| int fips_cipher_test(struct evp_cipher_ctx_st *ctx, | ||||
| 			const struct evp_cipher_st *cipher, | ||||
| 			const unsigned char *key, | ||||
| 			const unsigned char *iv, | ||||
| 			const unsigned char *plaintext, | ||||
| 			const unsigned char *ciphertext, | ||||
| 			int len); | ||||
| 
 | ||||
| void fips_set_selftest_fail(void); | ||||
| int fips_check_rsa(struct rsa_st *rsa); | ||||
| 
 | ||||
| void FIPS_evp_md_ctx_init(EVP_MD_CTX *ctx); | ||||
| EVP_MD_CTX *FIPS_evp_md_ctx_create(void); | ||||
| int FIPS_evp_digestinit_ex(EVP_MD_CTX *ctx, const EVP_MD *type, ENGINE *impl); | ||||
| int FIPS_evp_digestupdate(EVP_MD_CTX *ctx, const void *data, size_t count); | ||||
| int FIPS_evp_digestfinal(EVP_MD_CTX *ctx, | ||||
| 					unsigned char *md, unsigned int *size); | ||||
| int FIPS_evp_digest(const void *data, size_t count, | ||||
| 		unsigned char *md, unsigned int *size, const EVP_MD *type, ENGINE *impl); | ||||
| void FIPS_evp_md_ctx_destroy(EVP_MD_CTX *ctx); | ||||
| int FIPS_evp_md_ctx_cleanup(EVP_MD_CTX *ctx); | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS_SOURCE | ||||
| #define ENGINE_init FIPS_engine_init | ||||
| #define ENGINE_finish FIPS_engine_finish | ||||
| #define ENGINE_get_digest FIPS_engine_get_digest | ||||
| #define ENGINE_get_digest_engine FIPS_engine_get_digest_engine | ||||
| #define ENGINE_get_RAND FIPS_engine_get_rand | ||||
| #define ENGINE_get_default_RAND FIPS_engine_get_default_rand | ||||
| #define EVP_SignFinal FIPS_evp_signfinal | ||||
| #define EVP_VerifyFinal FIPS_evp_verifyfinal | ||||
| #endif | ||||
| 
 | ||||
| /* BEGIN ERROR CODES */ | ||||
| /* The following lines are auto generated by the script mkerr.pl. Any changes
 | ||||
|  * made after this point may be overwritten when the script is next run. | ||||
|  */ | ||||
| void ERR_load_FIPS_strings(void); | ||||
| 
 | ||||
| /* Error codes for the FIPS functions. */ | ||||
| 
 | ||||
| /* Function codes. */ | ||||
| #define FIPS_F_DH_BUILTIN_GENPARAMS			 100 | ||||
| #define FIPS_F_DSA_BUILTIN_PARAMGEN			 101 | ||||
| #define FIPS_F_DSA_DO_SIGN				 102 | ||||
| #define FIPS_F_DSA_DO_VERIFY				 103 | ||||
| #define FIPS_F_EVP_CIPHERINIT_EX			 124 | ||||
| #define FIPS_F_EVP_DIGESTINIT_EX			 125 | ||||
| #define FIPS_F_FIPS_CHECK_DSA				 104 | ||||
| #define FIPS_F_FIPS_CHECK_INCORE_FINGERPRINT		 105 | ||||
| #define FIPS_F_FIPS_CHECK_RSA				 106 | ||||
| #define FIPS_F_FIPS_DSA_CHECK				 107 | ||||
| #define FIPS_F_FIPS_MODE_SET				 108 | ||||
| #define FIPS_F_FIPS_PKEY_SIGNATURE_TEST			 109 | ||||
| #define FIPS_F_FIPS_SELFTEST_AES			 110 | ||||
| #define FIPS_F_FIPS_SELFTEST_DES			 111 | ||||
| #define FIPS_F_FIPS_SELFTEST_DSA			 112 | ||||
| #define FIPS_F_FIPS_SELFTEST_HMAC			 113 | ||||
| #define FIPS_F_FIPS_SELFTEST_RNG			 114 | ||||
| #define FIPS_F_FIPS_SELFTEST_SHA1			 115 | ||||
| #define FIPS_F_HASH_FINAL				 123 | ||||
| #define FIPS_F_RSA_BUILTIN_KEYGEN			 116 | ||||
| #define FIPS_F_RSA_EAY_PRIVATE_DECRYPT			 117 | ||||
| #define FIPS_F_RSA_EAY_PRIVATE_ENCRYPT			 118 | ||||
| #define FIPS_F_RSA_EAY_PUBLIC_DECRYPT			 119 | ||||
| #define FIPS_F_RSA_EAY_PUBLIC_ENCRYPT			 120 | ||||
| #define FIPS_F_RSA_X931_GENERATE_KEY_EX			 121 | ||||
| #define FIPS_F_SSLEAY_RAND_BYTES			 122 | ||||
| 
 | ||||
| /* Reason codes. */ | ||||
| #define FIPS_R_CANNOT_READ_EXE				 103 | ||||
| #define FIPS_R_CANNOT_READ_EXE_DIGEST			 104 | ||||
| #define FIPS_R_CONTRADICTING_EVIDENCE			 114 | ||||
| #define FIPS_R_EXE_DIGEST_DOES_NOT_MATCH		 105 | ||||
| #define FIPS_R_FINGERPRINT_DOES_NOT_MATCH		 110 | ||||
| #define FIPS_R_FINGERPRINT_DOES_NOT_MATCH_NONPIC_RELOCATED 111 | ||||
| #define FIPS_R_FINGERPRINT_DOES_NOT_MATCH_SEGMENT_ALIASING 112 | ||||
| #define FIPS_R_FIPS_MODE_ALREADY_SET			 102 | ||||
| #define FIPS_R_FIPS_SELFTEST_FAILED			 106 | ||||
| #define FIPS_R_INVALID_KEY_LENGTH			 109 | ||||
| #define FIPS_R_KEY_TOO_SHORT				 108 | ||||
| #define FIPS_R_NON_FIPS_METHOD				 100 | ||||
| #define FIPS_R_PAIRWISE_TEST_FAILED			 107 | ||||
| #define FIPS_R_RSA_DECRYPT_ERROR			 115 | ||||
| #define FIPS_R_RSA_ENCRYPT_ERROR			 116 | ||||
| #define FIPS_R_SELFTEST_FAILED				 101 | ||||
| #define FIPS_R_TEST_FAILURE				 117 | ||||
| #define FIPS_R_UNSUPPORTED_PLATFORM			 113 | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| } | ||||
| #endif | ||||
| #endif | ||||
|  | @ -0,0 +1,190 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project. Rights for redistribution | ||||
|  * and usage in source and binary forms are granted according to the | ||||
|  * OpenSSL license. | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #if defined(__DECC) | ||||
| # include <c_asm.h> | ||||
| # pragma __nostandard | ||||
| #endif | ||||
| 
 | ||||
| const void         *FIPS_text_start(void); | ||||
| const void         *FIPS_text_end(void); | ||||
| 
 | ||||
| #include "e_os.h" | ||||
| 
 | ||||
| #if !defined(POINTER_TO_FUNCTION_IS_POINTER_TO_1ST_INSTRUCTION) | ||||
| # if	(defined(__sun) && (defined(__sparc) || defined(__sparcv9)))	|| \ | ||||
| 	(defined(__sgi) && (defined(__mips) || defined(mips)))		|| \ | ||||
| 	(defined(__osf__) && defined(__alpha))				|| \ | ||||
| 	(defined(__linux) && (defined(__arm) || defined(__arm__)))	|| \ | ||||
| 	(defined(__i386) || defined(__i386__))				|| \ | ||||
| 	(defined(__x86_64) || defined(__x86_64__))			|| \ | ||||
| 	defined(__ANDROID__)						|| \ | ||||
| 	(defined(vax) || defined(__vax__)) | ||||
| #  define POINTER_TO_FUNCTION_IS_POINTER_TO_1ST_INSTRUCTION | ||||
| # endif | ||||
| #endif | ||||
| 
 | ||||
| #if defined(__xlC__) && __xlC__>=0x600 && (defined(_POWER) || defined(_ARCH_PPC)) | ||||
| static void *instruction_pointer_xlc(void); | ||||
| # pragma mc_func instruction_pointer_xlc {\ | ||||
| 	"7c0802a6"	/* mflr	r0  */	\ | ||||
| 	"48000005"	/* bl	$+4 */	\ | ||||
| 	"7c6802a6"	/* mflr	r3  */	\ | ||||
| 	"7c0803a6"	/* mtlr	r0  */	} | ||||
| # pragma reg_killed_by instruction_pointer_xlc gr0 gr3 | ||||
| # define INSTRUCTION_POINTER_IMPLEMENTED(ret) (ret=instruction_pointer_xlc()); | ||||
| #endif | ||||
| 
 | ||||
| #ifdef FIPS_START | ||||
| #define FIPS_ref_point FIPS_text_start | ||||
| /* Some compilers put string literals into a separate segment. As we
 | ||||
|  * are mostly interested to hash AES tables in .rodata, we declare | ||||
|  * reference points accordingly. In case you wonder, the values are | ||||
|  * big-endian encoded variable names, just to prevent these arrays | ||||
|  * from being merged by linker. */ | ||||
| const unsigned int FIPS_rodata_start[]= | ||||
| 	{ 0x46495053, 0x5f726f64, 0x6174615f, 0x73746172 }; | ||||
| #else | ||||
| #define FIPS_ref_point FIPS_text_end | ||||
| const unsigned int FIPS_rodata_end[]= | ||||
| 	{ 0x46495053, 0x5f726f64, 0x6174615f, 0x656e645b }; | ||||
| #endif | ||||
| 
 | ||||
| /*
 | ||||
|  * I declare reference function as static in order to avoid certain | ||||
|  * pitfalls in -dynamic linker behaviour... | ||||
|  */ | ||||
| static void *instruction_pointer(void) | ||||
| { void *ret=NULL; | ||||
| /* These are ABI-neutral CPU-specific snippets. ABI-neutrality means
 | ||||
|  * that they are designed to work under any OS running on particular | ||||
|  * CPU, which is why you don't find any #ifdef THIS_OR_THAT_OS in | ||||
|  * this function. */ | ||||
| #if	defined(INSTRUCTION_POINTER_IMPLEMENTED) | ||||
|     INSTRUCTION_POINTER_IMPLEMENTED(ret); | ||||
| #elif	defined(__GNUC__) && __GNUC__>=2 | ||||
| # if	defined(__alpha) || defined(__alpha__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"br	%0,1f\n1:" : "=r"(ret) ); | ||||
| # elif	defined(__i386) || defined(__i386__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"call 1f\n1:	popl %0" : "=r"(ret) ); | ||||
|     ret = (void *)((size_t)ret&~3UL); /* align for better performance */ | ||||
| # elif	defined(__ia64) || defined(__ia64__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"mov	%0=ip" : "=r"(ret) ); | ||||
| # elif	defined(__hppa) || defined(__hppa__) || defined(__pa_risc) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"blr	%%r0,%0\n\tnop" : "=r"(ret) ); | ||||
|     ret = (void *)((size_t)ret&~3UL); /* mask privilege level */ | ||||
| # elif	defined(__mips) || defined(__mips__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     void *scratch; | ||||
|     __asm __volatile (	"move	%1,$31\n\t"	/* save ra */ | ||||
| 			"bal	.+8; nop\n\t" | ||||
| 			"move	%0,$31\n\t" | ||||
| 			"move	$31,%1"		/* restore ra */ | ||||
| 			: "=r"(ret),"=r"(scratch) ); | ||||
| # elif	defined(__ppc__) || defined(__powerpc) || defined(__powerpc__) || \ | ||||
| 	defined(__POWERPC__) || defined(_POWER) || defined(__PPC__) || \ | ||||
| 	defined(__PPC64__) || defined(__powerpc64__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     void *scratch; | ||||
|     __asm __volatile (	"mfspr	%1,8\n\t"	/* save lr */ | ||||
| 			"bl	$+4\n\t" | ||||
| 			"mfspr	%0,8\n\t"	/* mflr ret */ | ||||
| 			"mtspr	8,%1"		/* restore lr */ | ||||
| 			: "=r"(ret),"=r"(scratch) ); | ||||
| # elif	defined(__s390__) || defined(__s390x__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"bras	%0,1f\n1:" : "=r"(ret) ); | ||||
|     ret = (void *)((size_t)ret&~3UL); | ||||
| # elif	defined(__sparc) || defined(__sparc__) || defined(__sparcv9) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     void *scratch; | ||||
|     __asm __volatile (	"mov	%%o7,%1\n\t" | ||||
| 			"call	.+8; nop\n\t" | ||||
| 		  	"mov	%%o7,%0\n\t" | ||||
| 			"mov	%1,%%o7" | ||||
| 			: "=r"(ret),"=r"(scratch) ); | ||||
| # elif	defined(__x86_64) || defined(__x86_64__) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     __asm __volatile (	"leaq	0(%%rip),%0" : "=r"(ret) ); | ||||
|     ret = (void *)((size_t)ret&~3UL); /* align for better performance */ | ||||
| # endif | ||||
| #elif	defined(__DECC) && defined(__alpha) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     ret = (void *)(size_t)asm("br %v0,1f\n1:"); | ||||
| #elif   defined(_MSC_VER) && defined(_M_IX86) | ||||
| #   define INSTRUCTION_POINTER_IMPLEMENTED | ||||
|     void *scratch; | ||||
|     _asm { | ||||
|             call    self | ||||
|     self:   pop     eax | ||||
|             mov     scratch,eax | ||||
|          } | ||||
|     ret = (void *)((size_t)scratch&~3UL); | ||||
| #endif | ||||
|   return ret; | ||||
| } | ||||
| 
 | ||||
| /*
 | ||||
|  * This function returns pointer to an instruction in the vicinity of | ||||
|  * its entry point, but not outside this object module. This guarantees | ||||
|  * that sequestered code is covered... | ||||
|  */ | ||||
| const void *FIPS_ref_point() | ||||
| { | ||||
| #if	defined(INSTRUCTION_POINTER_IMPLEMENTED) | ||||
|     return instruction_pointer(); | ||||
| /* Below we essentially cover vendor compilers which do not support
 | ||||
|  * inline assembler... */ | ||||
| #elif	defined(_AIX) | ||||
|     struct { void *ip,*gp,*env; } *p = (void *)instruction_pointer; | ||||
|     return p->ip; | ||||
| #elif	defined(_HPUX_SOURCE) | ||||
| # if	defined(__hppa) || defined(__hppa__) | ||||
|     struct { void *i[4]; } *p = (void *)FIPS_ref_point; | ||||
| 
 | ||||
|     if (sizeof(p) == 8)	/* 64-bit */ | ||||
| 	return p->i[2]; | ||||
|     else if ((size_t)p & 2) | ||||
|     {	p = (void *)((size_t)p&~3UL); | ||||
| 	return p->i[0]; | ||||
|     } | ||||
|     else | ||||
| 	return (void *)p; | ||||
| # elif	defined(__ia64) || defined(__ia64__) | ||||
|     struct { unsigned long long ip,gp; } *p=(void *)instruction_pointer; | ||||
|     return (void *)(size_t)p->ip; | ||||
| # endif | ||||
| #elif	(defined(__VMS) || defined(VMS)) && !(defined(vax) || defined(__vax__)) | ||||
|     /* applies to both alpha and ia64 */ | ||||
|     struct { unsigned __int64 opaque,ip; } *p=(void *)instruction_pointer; | ||||
|     return (void *)(size_t)p->ip; | ||||
| #elif	defined(__VOS__) | ||||
|     /* applies to both pa-risc and ia32 */ | ||||
|     struct { void *dp,*ip,*gp; } *p = (void *)instruction_pointer; | ||||
|     return p->ip; | ||||
| #elif	defined(_WIN32) | ||||
| # if	defined(_WIN64) && defined(_M_IA64) | ||||
|     struct { void *ip,*gp; } *p = (void *)FIPS_ref_point; | ||||
|     return p->ip; | ||||
| # else | ||||
|     return (void *)FIPS_ref_point; | ||||
| # endif | ||||
| /*
 | ||||
|  * In case you wonder why there is no #ifdef __linux. All Linux targets | ||||
|  * are GCC-based and therefore are covered by instruction_pointer above | ||||
|  * [well, some are covered by by the one below]... | ||||
|  */  | ||||
| #elif	defined(POINTER_TO_FUNCTION_IS_POINTER_TO_1ST_INSTRUCTION) | ||||
|     return (void *)instruction_pointer; | ||||
| #else | ||||
|     return NULL; | ||||
| #endif | ||||
| } | ||||
|  | @ -0,0 +1,72 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| extern "C" { | ||||
| #endif | ||||
| 
 | ||||
| void fips_w_lock(void); | ||||
| void fips_w_unlock(void); | ||||
| void fips_r_lock(void); | ||||
| void fips_r_unlock(void); | ||||
| int fips_is_started(void); | ||||
| void fips_set_started(void); | ||||
| int fips_is_owning_thread(void); | ||||
| int fips_set_owning_thread(void); | ||||
| int fips_clear_owning_thread(void); | ||||
| unsigned char *fips_signature_witness(void); | ||||
| 
 | ||||
| #define FIPS_MAX_CIPHER_TEST_SIZE	16 | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| } | ||||
| #endif | ||||
| #endif | ||||
|  | @ -0,0 +1,176 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project. Rights for redistribution | ||||
|  * and usage in source and binary forms are granted according to the | ||||
|  * OpenSSL license. | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #if defined(__unix) || defined(__unix__) | ||||
| #include <unistd.h> | ||||
| #endif | ||||
| 
 | ||||
| #ifndef FINGERPRINT_PREMAIN_DSO_LOAD | ||||
| 
 | ||||
| #if defined(__GNUC__) && __GNUC__>=2 | ||||
|   void FINGERPRINT_premain(void) __attribute__((constructor)); | ||||
|   /* Most commonly this results in pointer to premain to be dropped
 | ||||
|    * to .ctors segment, which is traversed by GCC crtbegin.o upon | ||||
|    * program startup. Except on a.out OpenBSD where it results in | ||||
|    * _GLOBAL_$I$premain() {premain();} being auto-generated by | ||||
|    * compiler... But one way or another this is believed to cover | ||||
|    * *all* GCC targets. */ | ||||
| #elif defined(_MSC_VER) | ||||
| # ifdef _WINDLL | ||||
|   __declspec(dllexport)	/* this is essentially cosmetics... */ | ||||
| # endif | ||||
|   void FINGERPRINT_premain(void); | ||||
|   static int premain_wrapper(void) { FINGERPRINT_premain(); return 0; } | ||||
| # ifdef _WIN64 | ||||
| # pragma section(".CRT$XCU",read) | ||||
|   __declspec(allocate(".CRT$XCU")) | ||||
| # else | ||||
| # pragma data_seg(".CRT$XCU") | ||||
| # endif | ||||
|   static int (*p)(void) = premain_wrapper; | ||||
|   /* This results in pointer to premain to appear in .CRT segment,
 | ||||
|    * which is traversed by Visual C run-time initialization code. | ||||
|    * This applies to both Win32 and [all flavors of] Win64. */ | ||||
| # pragma data_seg() | ||||
| #elif defined(__SUNPRO_C) | ||||
|   void FINGERPRINT_premain(void); | ||||
| # pragma init(FINGERPRINT_premain) | ||||
|   /* This results in a call to premain to appear in .init segment. */ | ||||
| #elif defined(__DECC) && (defined(__VMS) || defined(VMS)) | ||||
|   void FINGERPRINT_premain(void); | ||||
| # pragma __nostandard | ||||
|   globaldef { "LIB$INITIALIZ" } readonly _align (LONGWORD) | ||||
| 	int spare[8] = {0}; | ||||
|   globaldef { "LIB$INITIALIZE" } readonly _align (LONGWORD) | ||||
| 	void (*x_FINGERPRINT_premain)(void) = FINGERPRINT_premain; | ||||
|   /* Refer to LIB$INITIALIZE to ensure it exists in the image. */ | ||||
|   int lib$initialize(); | ||||
|   globaldef int (*lib_init_ref)() = lib$initialize; | ||||
| # pragma __standard | ||||
| #elif 0 | ||||
|   The rest has to be taken care of through command line: | ||||
| 
 | ||||
| 	-Wl,-init,FINGERPRINT_premain		on OSF1 and IRIX | ||||
| 	-Wl,+init,FINGERPRINT_premain		on HP-UX | ||||
| 	-Wl,-binitfini:FINGERPRINT_premain	on AIX | ||||
| 
 | ||||
|   On ELF platforms this results in a call to premain to appear in | ||||
|   .init segment... | ||||
| #endif | ||||
| 
 | ||||
| #ifndef HMAC_SHA1_SIG | ||||
| #define HMAC_SHA1_SIG "?have to make sure this string is unique" | ||||
| #endif | ||||
| 
 | ||||
| static const unsigned char FINGERPRINT_ascii_value[40] = HMAC_SHA1_SIG; | ||||
| 
 | ||||
| #define atox(c) ((c)>='a'?((c)-'a'+10):((c)>='A'?(c)-'A'+10:(c)-'0')) | ||||
| 
 | ||||
| extern const void         *FIPS_text_start(),  *FIPS_text_end(); | ||||
| extern const unsigned char FIPS_rodata_start[], FIPS_rodata_end[]; | ||||
| extern unsigned char       FIPS_signature[20]; | ||||
| extern unsigned int        FIPS_incore_fingerprint(unsigned char *,unsigned int); | ||||
| 
 | ||||
| /*
 | ||||
|  * As name suggests this code is executed prior main(). We use this | ||||
|  * opportunity to fingerprint sequestered code in virtual address | ||||
|  * space of target application. | ||||
|  */ | ||||
| void FINGERPRINT_premain(void) | ||||
| { unsigned char sig[sizeof(FIPS_signature)]; | ||||
|   const unsigned char * volatile p=FINGERPRINT_ascii_value; | ||||
|   unsigned int len=sizeof(sig),i; | ||||
| 
 | ||||
|     /* "volatilization" is done to disengage unwanted optimization... */ | ||||
|     if (*((volatile unsigned char *)p)=='?') | ||||
|     {	if (FIPS_text_start()==NULL) | ||||
| 	{   fprintf(stderr,"FIPS_text_start() returns NULL\n"); | ||||
| 	    _exit(1); | ||||
| 	} | ||||
| #if defined(DEBUG_FINGERPRINT_PREMAIN) | ||||
| 	fprintf(stderr,".text:%p+%d=%p\n",FIPS_text_start(), | ||||
| 		(int)((size_t)FIPS_text_end()-(size_t)FIPS_text_start()), | ||||
| 		FIPS_text_end()); | ||||
| 	fprintf(stderr,".rodata:%p+%d=%p\n",FIPS_rodata_start, | ||||
| 		(int)((size_t)FIPS_rodata_end-(size_t)FIPS_rodata_start), | ||||
| 		FIPS_rodata_end); | ||||
| #endif | ||||
| 
 | ||||
| 	len=FIPS_incore_fingerprint(sig,sizeof(sig)); | ||||
| 
 | ||||
| 	if (len!=sizeof(sig)) | ||||
| 	{   fprintf(stderr,"fingerprint length mismatch: %u\n",len); | ||||
| 	    _exit(1); | ||||
| 	} | ||||
| 
 | ||||
| 	for (i=0;i<len;i++) printf("%02x",sig[i]); | ||||
| 	printf("\n"); | ||||
| 	fflush(stdout); | ||||
| 	_exit(0); | ||||
|     } | ||||
|     else if (FIPS_signature[0]=='\0') do | ||||
|     {	for (i=0;i<sizeof(FIPS_signature);i++,p+=2) | ||||
| 	    FIPS_signature[i] = (atox(p[0])<<4)|atox(p[1]); | ||||
| 
 | ||||
| #if defined(DEBUG_FINGERPRINT_PREMAIN) | ||||
| 	if (getenv("OPENSSL_FIPS")==NULL) break; | ||||
| 
 | ||||
| 	len=FIPS_incore_fingerprint(sig,sizeof(sig)); | ||||
| 
 | ||||
| 	if (memcmp(FIPS_signature,sig,sizeof(FIPS_signature))) | ||||
| 	{   fprintf(stderr,"FINGERPRINT_premain: FIPS_signature mismatch\n"); | ||||
| 	    _exit(1); | ||||
| 	} | ||||
| #endif | ||||
|     } while(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/dso.h> | ||||
| #include <openssl/err.h> | ||||
| 
 | ||||
| int main(int argc,char *argv[]) | ||||
| { DSO *dso; | ||||
|   DSO_FUNC_TYPE func; | ||||
|   BIO *bio_err; | ||||
| 
 | ||||
|     if (argc < 2) | ||||
|     {	fprintf (stderr,"usage: %s libcrypto.dso\n",argv[0]); | ||||
| 	return 1; | ||||
|     } | ||||
| 
 | ||||
|     if ((bio_err=BIO_new(BIO_s_file())) == NULL) | ||||
|     {	fprintf (stderr,"unable to allocate BIO\n"); | ||||
| 	return 1; | ||||
|     } | ||||
|     BIO_set_fp(bio_err,stderr,BIO_NOCLOSE|BIO_FP_TEXT); | ||||
|     ERR_load_crypto_strings(); | ||||
| 
 | ||||
|     dso = DSO_load(NULL,argv[1],NULL,DSO_FLAG_NO_NAME_TRANSLATION); | ||||
|     if (dso == NULL) | ||||
|     {	ERR_print_errors(bio_err); | ||||
| 	return 1; | ||||
|     } | ||||
| 
 | ||||
|     /* This is not normally reached, because FINGERPRINT_premain should
 | ||||
|      * have executed and terminated application already upon DSO_load... */ | ||||
|     func = DSO_bind_func(dso,"FINGERPRINT_premain"); | ||||
|     if (func == NULL) | ||||
|     {	ERR_print_errors(bio_err); | ||||
| 	return 1; | ||||
|     } | ||||
| 
 | ||||
|     (*func)(); | ||||
| 
 | ||||
|   return 0; | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,576 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * | ||||
|  * This command is intended as a test driver for the FIPS-140 testing | ||||
|  * lab performing FIPS-140 validation.  It demonstrates the use of the | ||||
|  * OpenSSL library ito perform a variety of common cryptographic | ||||
|  * functions.  A power-up self test is demonstrated by deliberately | ||||
|  * pointing to an invalid executable hash | ||||
|  * | ||||
|  * Contributed by Steve Marquess. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <assert.h> | ||||
| #include <ctype.h> | ||||
| #include <string.h> | ||||
| #include <stdlib.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/sha.h> | ||||
| #include <openssl/err.h> | ||||
| 
 | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/rand.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| int main(int argc, char *argv[]) | ||||
|     { | ||||
|     printf("No FIPS support\n"); | ||||
|     return(0); | ||||
|     } | ||||
| #else | ||||
| 
 | ||||
| #define ERR_clear_error() while(0) | ||||
| 
 | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/dh.h> | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| /* AES: encrypt and decrypt known plaintext, verify result matches original plaintext
 | ||||
| */ | ||||
| static int FIPS_aes_test(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	unsigned char pltmp[16]; | ||||
| 	unsigned char citmp[16]; | ||||
| 	unsigned char key[16] = { 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16}; | ||||
| 	unsigned char plaintext[16] = "etaonrishdlcu"; | ||||
| 	EVP_CIPHER_CTX ctx; | ||||
| 	EVP_CIPHER_CTX_init(&ctx); | ||||
| 	if (EVP_CipherInit_ex(&ctx, EVP_aes_128_ecb(),NULL, key, NULL, 1) <= 0) | ||||
| 		goto err; | ||||
| 	EVP_Cipher(&ctx, citmp, plaintext, 16); | ||||
| 	if (EVP_CipherInit_ex(&ctx, EVP_aes_128_ecb(),NULL, key, NULL, 0) <= 0) | ||||
| 		goto err; | ||||
| 	EVP_Cipher(&ctx, pltmp, citmp, 16); | ||||
| 	if (memcmp(pltmp, plaintext, 16)) | ||||
| 		goto err; | ||||
| 	ret = 1; | ||||
| 	err: | ||||
| 	EVP_CIPHER_CTX_cleanup(&ctx); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| static int FIPS_des3_test(void) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	unsigned char pltmp[8]; | ||||
| 	unsigned char citmp[8]; | ||||
|     	unsigned char key[] = { 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18, | ||||
| 		              19,20,21,22,23,24}; | ||||
|     	unsigned char plaintext[] = { 'e', 't', 'a', 'o', 'n', 'r', 'i', 's' }; | ||||
| 	EVP_CIPHER_CTX ctx; | ||||
| 	EVP_CIPHER_CTX_init(&ctx); | ||||
| 	if (EVP_CipherInit_ex(&ctx, EVP_des_ede3_ecb(),NULL, key, NULL, 1) <= 0) | ||||
| 		goto err; | ||||
| 	EVP_Cipher(&ctx, citmp, plaintext, 8); | ||||
| 	if (EVP_CipherInit_ex(&ctx, EVP_des_ede3_ecb(),NULL, key, NULL, 0) <= 0) | ||||
| 		goto err; | ||||
| 	EVP_Cipher(&ctx, pltmp, citmp, 8); | ||||
| 	if (memcmp(pltmp, plaintext, 8)) | ||||
| 		goto err; | ||||
| 	ret = 1; | ||||
| 	err: | ||||
| 	EVP_CIPHER_CTX_cleanup(&ctx); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| /*
 | ||||
|  * DSA: generate keys and sign, verify input plaintext. | ||||
|  */ | ||||
| static int FIPS_dsa_test(int bad) | ||||
|     { | ||||
|     DSA *dsa = NULL; | ||||
|     unsigned char dgst[] = "etaonrishdlc"; | ||||
|     int r = 0; | ||||
|     EVP_MD_CTX mctx; | ||||
|     DSA_SIG *sig = NULL; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     EVP_MD_CTX_init(&mctx); | ||||
|     dsa = FIPS_dsa_new(); | ||||
|     if (!dsa) | ||||
| 	goto end; | ||||
|     if (!DSA_generate_parameters_ex(dsa, 1024,NULL,0,NULL,NULL,NULL)) | ||||
| 	goto end; | ||||
|     if (!DSA_generate_key(dsa)) | ||||
| 	goto end; | ||||
|     if (bad) | ||||
| 	    BN_add_word(dsa->pub_key, 1); | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto end; | ||||
|     if (!EVP_DigestUpdate(&mctx, dgst, sizeof(dgst) - 1)) | ||||
| 	goto end; | ||||
|     sig = FIPS_dsa_sign_ctx(dsa, &mctx); | ||||
|     if (!sig) | ||||
| 	goto end; | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto end; | ||||
|     if (!EVP_DigestUpdate(&mctx, dgst, sizeof(dgst) - 1)) | ||||
| 	goto end; | ||||
|     r = FIPS_dsa_verify_ctx(dsa, &mctx, sig); | ||||
|     end: | ||||
|     if (sig) | ||||
| 	DSA_SIG_free(sig); | ||||
|     EVP_MD_CTX_cleanup(&mctx); | ||||
|     if (dsa) | ||||
|   	  FIPS_dsa_free(dsa); | ||||
|     if (r != 1) | ||||
| 	return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /*
 | ||||
|  * RSA: generate keys and sign, verify input plaintext. | ||||
|  */ | ||||
| static int FIPS_rsa_test(int bad) | ||||
|     { | ||||
|     RSA *key; | ||||
|     unsigned char input_ptext[] = "etaonrishdlc"; | ||||
|     unsigned char buf[256]; | ||||
|     unsigned int slen; | ||||
|     BIGNUM *bn; | ||||
|     EVP_MD_CTX mctx; | ||||
|     int r = 0; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     EVP_MD_CTX_init(&mctx); | ||||
|     key = FIPS_rsa_new(); | ||||
|     bn = BN_new(); | ||||
|     if (!key || !bn) | ||||
| 	return 0; | ||||
|     BN_set_word(bn, 65537); | ||||
|     if (!RSA_generate_key_ex(key, 1024,bn,NULL)) | ||||
| 	return 0; | ||||
|     BN_free(bn); | ||||
|     if (bad) | ||||
| 	    BN_add_word(key->n, 1); | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto end; | ||||
|     if (!EVP_DigestUpdate(&mctx, input_ptext, sizeof(input_ptext) - 1)) | ||||
| 	goto end; | ||||
|     if (!FIPS_rsa_sign_ctx(key, &mctx, RSA_PKCS1_PADDING, 0, NULL, buf, &slen)) | ||||
| 	goto end; | ||||
| 
 | ||||
|     if (!EVP_DigestInit_ex(&mctx, EVP_sha1(), NULL)) | ||||
| 	goto end; | ||||
|     if (!EVP_DigestUpdate(&mctx, input_ptext, sizeof(input_ptext) - 1)) | ||||
| 	goto end; | ||||
|     r = FIPS_rsa_verify_ctx(key, &mctx, RSA_PKCS1_PADDING, 0, NULL, buf, slen); | ||||
|     end: | ||||
|     EVP_MD_CTX_cleanup(&mctx); | ||||
|     if (key) | ||||
|   	  FIPS_rsa_free(key); | ||||
|     if (r != 1) | ||||
| 	return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* SHA1: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_sha1_test() | ||||
|     { | ||||
|     unsigned char digest[SHA_DIGEST_LENGTH] = | ||||
|         { 0x11, 0xf1, 0x9a, 0x3a, 0xec, 0x1a, 0x1e, 0x8e, 0x65, 0xd4, 0x9a, 0x38, 0x0c, 0x8b, 0x1e, 0x2c, 0xe8, 0xb3, 0xc5, 0x18 }; | ||||
|     unsigned char str[] = "etaonrishd"; | ||||
| 
 | ||||
|     unsigned char md[SHA_DIGEST_LENGTH]; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!EVP_Digest(str,sizeof(str) - 1,md, NULL, EVP_sha1(), NULL)) return 0; | ||||
|     if (memcmp(md,digest,sizeof(md))) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* SHA256: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_sha256_test() | ||||
|     { | ||||
|     unsigned char digest[SHA256_DIGEST_LENGTH] = | ||||
| 	{0xf5, 0x53, 0xcd, 0xb8, 0xcf, 0x1, 0xee, 0x17, 0x9b, 0x93, 0xc9, 0x68, 0xc0, 0xea, 0x40, 0x91, | ||||
| 	 0x6, 0xec, 0x8e, 0x11, 0x96, 0xc8, 0x5d, 0x1c, 0xaf, 0x64, 0x22, 0xe6, 0x50, 0x4f, 0x47, 0x57}; | ||||
|     unsigned char str[] = "etaonrishd"; | ||||
| 
 | ||||
|     unsigned char md[SHA256_DIGEST_LENGTH]; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!EVP_Digest(str,sizeof(str) - 1,md, NULL, EVP_sha256(), NULL)) return 0; | ||||
|     if (memcmp(md,digest,sizeof(md))) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* SHA512: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_sha512_test() | ||||
|     { | ||||
|     unsigned char digest[SHA512_DIGEST_LENGTH] = | ||||
| 	{0x99, 0xc9, 0xe9, 0x5b, 0x88, 0xd4, 0x78, 0x88, 0xdf, 0x88, 0x5f, 0x94, 0x71, 0x64, 0x28, 0xca, | ||||
| 	 0x16, 0x1f, 0x3d, 0xf4, 0x1f, 0xf3, 0x0f, 0xc5, 0x03, 0x99, 0xb2, 0xd0, 0xe7, 0x0b, 0x94, 0x4a, | ||||
| 	 0x45, 0xd2, 0x6c, 0x4f, 0x20, 0x06, 0xef, 0x71, 0xa9, 0x25, 0x7f, 0x24, 0xb1, 0xd9, 0x40, 0x22, | ||||
| 	 0x49, 0x54, 0x10, 0xc2, 0x22, 0x9d, 0x27, 0xfe, 0xbd, 0xd6, 0xd6, 0xeb, 0x2d, 0x42, 0x1d, 0xa3}; | ||||
|     unsigned char str[] = "etaonrishd"; | ||||
| 
 | ||||
|     unsigned char md[SHA512_DIGEST_LENGTH]; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!EVP_Digest(str,sizeof(str) - 1,md, NULL, EVP_sha512(), NULL)) return 0; | ||||
|     if (memcmp(md,digest,sizeof(md))) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* HMAC-SHA1: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_hmac_sha1_test() | ||||
|     { | ||||
|     unsigned char key[] = "etaonrishd"; | ||||
|     unsigned char iv[] = "Sample text"; | ||||
|     unsigned char kaval[EVP_MAX_MD_SIZE] = | ||||
| 	{0x73, 0xf7, 0xa0, 0x48, 0xf8, 0x94, 0xed, 0xdd, 0x0a, 0xea, 0xea, 0x56, 0x1b, 0x61, 0x2e, 0x70, | ||||
| 	 0xb2, 0xfb, 0xec, 0xc6}; | ||||
| 
 | ||||
|     unsigned char out[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int outlen; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!HMAC(EVP_sha1(),key,sizeof(key)-1,iv,sizeof(iv)-1,out,&outlen)) return 0; | ||||
|     if (memcmp(out,kaval,outlen)) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* HMAC-SHA224: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_hmac_sha224_test() | ||||
|     { | ||||
|     unsigned char key[] = "etaonrishd"; | ||||
|     unsigned char iv[] = "Sample text"; | ||||
|     unsigned char kaval[EVP_MAX_MD_SIZE] = | ||||
| 	{0x75, 0x58, 0xd5, 0xbd, 0x55, 0x6d, 0x87, 0x0f, 0x75, 0xff, 0xbe, 0x1c, 0xb2, 0xf0, 0x20, 0x35, | ||||
| 	 0xe5, 0x62, 0x49, 0xb6, 0x94, 0xb9, 0xfc, 0x65, 0x34, 0x33, 0x3a, 0x19}; | ||||
| 
 | ||||
|     unsigned char out[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int outlen; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!HMAC(EVP_sha224(),key,sizeof(key)-1,iv,sizeof(iv)-1,out,&outlen)) return 0; | ||||
|     if (memcmp(out,kaval,outlen)) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* HMAC-SHA256: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_hmac_sha256_test() | ||||
|     { | ||||
|     unsigned char key[] = "etaonrishd"; | ||||
|     unsigned char iv[] = "Sample text"; | ||||
|     unsigned char kaval[EVP_MAX_MD_SIZE] = | ||||
| 	{0xe9, 0x17, 0xc1, 0x7b, 0x4c, 0x6b, 0x77, 0xda, 0xd2, 0x30, 0x36, 0x02, 0xf5, 0x72, 0x33, 0x87, | ||||
| 	 0x9f, 0xc6, 0x6e, 0x7b, 0x7e, 0xa8, 0xea, 0xaa, 0x9f, 0xba, 0xee, 0x51, 0xff, 0xda, 0x24, 0xf4}; | ||||
| 
 | ||||
|     unsigned char out[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int outlen; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!HMAC(EVP_sha256(),key,sizeof(key)-1,iv,sizeof(iv)-1,out,&outlen)) return 0; | ||||
|     if (memcmp(out,kaval,outlen)) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* HMAC-SHA384: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_hmac_sha384_test() | ||||
|     { | ||||
|     unsigned char key[] = "etaonrishd"; | ||||
|     unsigned char iv[] = "Sample text"; | ||||
|     unsigned char kaval[EVP_MAX_MD_SIZE] = | ||||
| 	{0xb2, 0x9d, 0x40, 0x58, 0x32, 0xc4, 0xe3, 0x31, 0xb6, 0x63, 0x08, 0x26, 0x99, 0xef, 0x3b, 0x10, | ||||
| 	 0xe2, 0xdf, 0xf8, 0xff, 0xc6, 0xe1, 0x03, 0x29, 0x81, 0x2a, 0x1b, 0xac, 0xb0, 0x07, 0x39, 0x08, | ||||
| 	 0xf3, 0x91, 0x35, 0x11, 0x76, 0xd6, 0x4c, 0x20, 0xfb, 0x4d, 0xc3, 0xf3, 0xb8, 0x9b, 0x88, 0x1c}; | ||||
| 
 | ||||
|     unsigned char out[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int outlen; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!HMAC(EVP_sha384(),key,sizeof(key)-1,iv,sizeof(iv)-1,out,&outlen)) return 0; | ||||
|     if (memcmp(out,kaval,outlen)) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* HMAC-SHA512: generate hash of known digest value and compare to known
 | ||||
|    precomputed correct hash | ||||
| */ | ||||
| static int FIPS_hmac_sha512_test() | ||||
|     { | ||||
|     unsigned char key[] = "etaonrishd"; | ||||
|     unsigned char iv[] = "Sample text"; | ||||
|     unsigned char kaval[EVP_MAX_MD_SIZE] = | ||||
| 	{0xcd, 0x3e, 0xb9, 0x51, 0xb8, 0xbc, 0x7f, 0x9a, 0x23, 0xaf, 0xf3, 0x77, 0x59, 0x85, 0xa9, 0xe6, | ||||
| 	 0xf7, 0xd1, 0x51, 0x96, 0x17, 0xe0, 0x92, 0xd8, 0xa6, 0x3b, 0xc1, 0xad, 0x7e, 0x24, 0xca, 0xb1, | ||||
| 	 0xd7, 0x79, 0x0a, 0xa5, 0xea, 0x2c, 0x02, 0x58, 0x0b, 0xa6, 0x52, 0x6b, 0x61, 0x7f, 0xeb, 0x9c, | ||||
| 	 0x47, 0x86, 0x5d, 0x74, 0x2b, 0x88, 0xdf, 0xee, 0x46, 0x69, 0x96, 0x3d, 0xa6, 0xd9, 0x2a, 0x53}; | ||||
| 
 | ||||
|     unsigned char out[EVP_MAX_MD_SIZE]; | ||||
|     unsigned int outlen; | ||||
| 
 | ||||
|     ERR_clear_error(); | ||||
|     if (!HMAC(EVP_sha512(),key,sizeof(key)-1,iv,sizeof(iv)-1,out,&outlen)) return 0; | ||||
|     if (memcmp(out,kaval,outlen)) | ||||
|         return 0; | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| /* DH: generate shared parameters
 | ||||
| */ | ||||
| static int dh_test() | ||||
|     { | ||||
|     DH *dh; | ||||
|     ERR_clear_error(); | ||||
|     dh = FIPS_dh_new(); | ||||
|     if (!dh) | ||||
| 	return 0; | ||||
|     if (!DH_generate_parameters_ex(dh, 1024, 2, NULL)) | ||||
| 	return 0; | ||||
|     FIPS_dh_free(dh); | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| /* Zeroize
 | ||||
| */ | ||||
| static int Zeroize() | ||||
|     { | ||||
|     RSA *key; | ||||
|     BIGNUM *bn; | ||||
|     unsigned char userkey[16] =  | ||||
| 	{ 0x48, 0x50, 0xf0, 0xa3, 0x3a, 0xed, 0xd3, 0xaf, 0x6e, 0x47, 0x7f, 0x83, 0x02, 0xb1, 0x09, 0x68 }; | ||||
|     size_t i; | ||||
|     int n; | ||||
| 
 | ||||
|     key = FIPS_rsa_new(); | ||||
|     bn = BN_new(); | ||||
|     if (!key || !bn) | ||||
| 	return 0; | ||||
|     BN_set_word(bn, 65537); | ||||
|     if (!RSA_generate_key_ex(key, 1024,bn,NULL)) | ||||
| 	return 0; | ||||
|     BN_free(bn); | ||||
|      | ||||
|     n = BN_num_bytes(key->d); | ||||
|     printf(" Generated %d byte RSA private key\n", n); | ||||
|     printf("\tBN key before overwriting:\n"); | ||||
|     do_bn_print(stdout, key->d); | ||||
|     BN_rand(key->d,n*8,-1,0); | ||||
|     printf("\tBN key after overwriting:\n"); | ||||
|     do_bn_print(stdout, key->d); | ||||
| 
 | ||||
|     printf("\tchar buffer key before overwriting: \n\t\t"); | ||||
|     for(i = 0; i < sizeof(userkey); i++) printf("%02x", userkey[i]); | ||||
|         printf("\n"); | ||||
|     RAND_bytes(userkey, sizeof userkey); | ||||
|     printf("\tchar buffer key after overwriting: \n\t\t"); | ||||
|     for(i = 0; i < sizeof(userkey); i++) printf("%02x", userkey[i]); | ||||
|         printf("\n"); | ||||
| 
 | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| static int Error; | ||||
| static const char * Fail(const char *msg) | ||||
|     { | ||||
|     Error++; | ||||
|     return msg;  | ||||
|     } | ||||
| 
 | ||||
| static void test_msg(const char *msg, int result) | ||||
| 	{ | ||||
| 	printf("%s...%s\n", msg, result ? "successful" : Fail("Failed!")); | ||||
| 	} | ||||
| 
 | ||||
| int main(int argc,char **argv) | ||||
|     { | ||||
| 
 | ||||
|     int do_corrupt_rsa_keygen = 0, do_corrupt_dsa_keygen = 0; | ||||
|     int bad_rsa = 0, bad_dsa = 0; | ||||
|     int do_rng_stick = 0; | ||||
|     int no_exit = 0; | ||||
| 
 | ||||
|     fips_set_error_print(); | ||||
| 
 | ||||
|     printf("\tFIPS-mode test application\n\n"); | ||||
| 
 | ||||
|     /* Load entropy from external file, if any */ | ||||
|     RAND_load_file(".rnd", 1024); | ||||
| 
 | ||||
|     if (argv[1]) { | ||||
|         /* Corrupted KAT tests */ | ||||
|         if (!strcmp(argv[1], "aes")) { | ||||
|             FIPS_corrupt_aes(); | ||||
|             printf("AES encryption/decryption with corrupted KAT...\n"); | ||||
|         } else if (!strcmp(argv[1], "des")) { | ||||
|             FIPS_corrupt_des(); | ||||
|             printf("DES3-ECB encryption/decryption with corrupted KAT...\n"); | ||||
|         } else if (!strcmp(argv[1], "dsa")) { | ||||
|             FIPS_corrupt_dsa(); | ||||
|             printf("DSA key generation and signature validation with corrupted KAT...\n"); | ||||
|         } else if (!strcmp(argv[1], "rsa")) { | ||||
|             FIPS_corrupt_rsa(); | ||||
|             printf("RSA key generation and signature validation with corrupted KAT...\n"); | ||||
|         } else if (!strcmp(argv[1], "rsakey")) { | ||||
|             printf("RSA key generation and signature validation with corrupted key...\n"); | ||||
| 	    bad_rsa = 1; | ||||
| 	    no_exit = 1; | ||||
|         } else if (!strcmp(argv[1], "rsakeygen")) { | ||||
| 	    do_corrupt_rsa_keygen = 1; | ||||
| 	    no_exit = 1; | ||||
|             printf("RSA key generation and signature validation with corrupted keygen...\n"); | ||||
|         } else if (!strcmp(argv[1], "dsakey")) { | ||||
|             printf("DSA key generation and signature validation with corrupted key...\n"); | ||||
| 	    bad_dsa = 1; | ||||
| 	    no_exit = 1; | ||||
|         } else if (!strcmp(argv[1], "dsakeygen")) { | ||||
| 	    do_corrupt_dsa_keygen = 1; | ||||
| 	    no_exit = 1; | ||||
|             printf("DSA key generation and signature validation with corrupted keygen...\n"); | ||||
|         } else if (!strcmp(argv[1], "sha1")) { | ||||
|             FIPS_corrupt_sha1(); | ||||
|             printf("SHA-1 hash with corrupted KAT...\n"); | ||||
| 	} else if (!strcmp(argv[1], "rng")) { | ||||
| 	    FIPS_corrupt_rng(); | ||||
| 	} else if (!strcmp(argv[1], "rngstick")) { | ||||
| 	    do_rng_stick = 1; | ||||
| 	    no_exit = 1; | ||||
| 	    printf("RNG test with stuck continuous test...\n"); | ||||
|         } else { | ||||
|             printf("Bad argument \"%s\"\n", argv[1]); | ||||
|             exit(1); | ||||
|         } | ||||
| 	if (!no_exit) { | ||||
|         	if (!FIPS_mode_set(1)) { | ||||
|         	    printf("Power-up self test failed\n"); | ||||
| 		    exit(1); | ||||
| 		} | ||||
|         	printf("Power-up self test successful\n"); | ||||
|         	exit(0); | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
|     /* Non-Approved cryptographic operation
 | ||||
|     */ | ||||
|     printf("1. Non-Approved cryptographic operation test...\n"); | ||||
|     test_msg("\ta. Included algorithm (D-H)...", dh_test()); | ||||
| 
 | ||||
|     /* Power-up self test
 | ||||
|     */ | ||||
|     ERR_clear_error(); | ||||
|     test_msg("2. Automatic power-up self test", FIPS_mode_set(1)); | ||||
|     if (!FIPS_mode()) | ||||
| 	exit(1); | ||||
|     if (do_corrupt_dsa_keygen) | ||||
|             FIPS_corrupt_dsa_keygen(); | ||||
|     if (do_corrupt_rsa_keygen) | ||||
|             FIPS_corrupt_rsa_keygen(); | ||||
|     if (do_rng_stick) | ||||
|             FIPS_rng_stick(); | ||||
| 
 | ||||
|     /* AES encryption/decryption
 | ||||
|     */ | ||||
|     test_msg("3. AES encryption/decryption", FIPS_aes_test()); | ||||
| 
 | ||||
|     /* RSA key generation and encryption/decryption
 | ||||
|     */ | ||||
|     test_msg("4. RSA key generation and encryption/decryption", | ||||
| 						FIPS_rsa_test(bad_rsa)); | ||||
| 
 | ||||
|     /* DES-CBC encryption/decryption
 | ||||
|     */ | ||||
|     test_msg("5. DES-ECB encryption/decryption", FIPS_des3_test()); | ||||
| 
 | ||||
|     /* DSA key generation and signature validation
 | ||||
|     */ | ||||
|     test_msg("6. DSA key generation and signature validation", | ||||
|     						FIPS_dsa_test(bad_dsa)); | ||||
| 
 | ||||
|     /* SHA-1 hash
 | ||||
|     */ | ||||
|     test_msg("7a. SHA-1 hash", FIPS_sha1_test()); | ||||
| 
 | ||||
|     /* SHA-256 hash
 | ||||
|     */ | ||||
|     test_msg("7b. SHA-256 hash", FIPS_sha256_test()); | ||||
| 
 | ||||
|     /* SHA-512 hash
 | ||||
|     */ | ||||
|     test_msg("7c. SHA-512 hash", FIPS_sha512_test()); | ||||
| 
 | ||||
|     /* HMAC-SHA-1 hash
 | ||||
|     */ | ||||
|     test_msg("7d. HMAC-SHA-1 hash", FIPS_hmac_sha1_test()); | ||||
| 
 | ||||
|     /* HMAC-SHA-224 hash
 | ||||
|     */ | ||||
|     test_msg("7e. HMAC-SHA-224 hash", FIPS_hmac_sha224_test()); | ||||
| 
 | ||||
|     /* HMAC-SHA-256 hash
 | ||||
|     */ | ||||
|     test_msg("7f. HMAC-SHA-256 hash", FIPS_hmac_sha256_test()); | ||||
| 
 | ||||
|     /* HMAC-SHA-384 hash
 | ||||
|     */ | ||||
|     test_msg("7g. HMAC-SHA-384 hash", FIPS_hmac_sha384_test()); | ||||
| 
 | ||||
|     /* HMAC-SHA-512 hash
 | ||||
|     */ | ||||
|     test_msg("7h. HMAC-SHA-512 hash", FIPS_hmac_sha512_test()); | ||||
| 
 | ||||
|     /* Non-Approved cryptographic operation
 | ||||
|     */ | ||||
|     printf("8. Non-Approved cryptographic operation test...\n"); | ||||
|     printf("\ta. Included algorithm (D-H)...%s\n", | ||||
|     		dh_test() ? "successful as expected" | ||||
| 	    					: Fail("failed INCORRECTLY!") ); | ||||
| 
 | ||||
|     /* Zeroization
 | ||||
|     */ | ||||
|     printf("9. Zero-ization...\n\t%s\n", | ||||
|     		Zeroize() ? "successful as expected" | ||||
| 					: Fail("failed INCORRECTLY!") ); | ||||
| 
 | ||||
|     printf("\nAll tests completed with %d errors\n", Error); | ||||
|     return Error ? 1 : 0; | ||||
|     } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,376 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| int hex2bin(const char *in, unsigned char *out); | ||||
| unsigned char *hex2bin_m(const char *in, long *plen); | ||||
| int do_hex2bn(BIGNUM **pr, const char *in); | ||||
| int do_bn_print(FILE *out, BIGNUM *bn); | ||||
| int do_bn_print_name(FILE *out, const char *name, BIGNUM *bn); | ||||
| int parse_line(char **pkw, char **pval, char *linebuf, char *olinebuf); | ||||
| BIGNUM *hex2bn(const char *in); | ||||
| int bin2hex(const unsigned char *in,int len,char *out); | ||||
| void pv(const char *tag,const unsigned char *val,int len); | ||||
| int tidy_line(char *linebuf, char *olinebuf); | ||||
| int bint2bin(const char *in, int len, unsigned char *out); | ||||
| int bin2bint(const unsigned char *in,int len,char *out); | ||||
| void PrintValue(char *tag, unsigned char *val, int len); | ||||
| void OutputValue(char *tag, unsigned char *val, int len, FILE *rfp,int bitmode); | ||||
| 
 | ||||
| static int no_err; | ||||
| 
 | ||||
| static void put_err_cb(int lib, int func,int reason,const char *file,int line) | ||||
| 	{ | ||||
| 		if (no_err) | ||||
| 			return; | ||||
| 		fprintf(stderr, "ERROR:lib=%d,func=%d,reason=%d" | ||||
| 				":file=%s:line=%d\n", | ||||
| 			lib, func, reason, file, line); | ||||
| 	} | ||||
| 
 | ||||
| static void add_err_cb(int num, va_list args) | ||||
| 	{ | ||||
| 	int i; | ||||
| 	char *str; | ||||
| 	if (no_err) | ||||
| 		return; | ||||
| 	fputs("\t", stderr); | ||||
| 	for (i = 0; i < num; i++) | ||||
| 		{ | ||||
| 		str = va_arg(args, char *); | ||||
| 		if (str) | ||||
| 			fputs(str, stderr); | ||||
| 		} | ||||
| 	fputs("\n", stderr); | ||||
| 	} | ||||
| 
 | ||||
| static void fips_set_error_print(void) | ||||
| 	{ | ||||
| 	FIPS_set_error_callbacks(put_err_cb, add_err_cb); | ||||
| 	} | ||||
| 
 | ||||
| int hex2bin(const char *in, unsigned char *out) | ||||
|     { | ||||
|     int n1, n2; | ||||
|     unsigned char ch; | ||||
| 
 | ||||
|     for (n1=0,n2=0 ; in[n1] && in[n1] != '\n' ; ) | ||||
| 	{ /* first byte */ | ||||
| 	if ((in[n1] >= '0') && (in[n1] <= '9')) | ||||
| 	    ch = in[n1++] - '0'; | ||||
| 	else if ((in[n1] >= 'A') && (in[n1] <= 'F')) | ||||
| 	    ch = in[n1++] - 'A' + 10; | ||||
| 	else if ((in[n1] >= 'a') && (in[n1] <= 'f')) | ||||
| 	    ch = in[n1++] - 'a' + 10; | ||||
| 	else | ||||
| 	    return -1; | ||||
| 	if(!in[n1]) | ||||
| 	    { | ||||
| 	    out[n2++]=ch; | ||||
| 	    break; | ||||
| 	    } | ||||
| 	out[n2] = ch << 4; | ||||
| 	/* second byte */ | ||||
| 	if ((in[n1] >= '0') && (in[n1] <= '9')) | ||||
| 	    ch = in[n1++] - '0'; | ||||
| 	else if ((in[n1] >= 'A') && (in[n1] <= 'F')) | ||||
| 	    ch = in[n1++] - 'A' + 10; | ||||
| 	else if ((in[n1] >= 'a') && (in[n1] <= 'f')) | ||||
| 	    ch = in[n1++] - 'a' + 10; | ||||
| 	else | ||||
| 	    return -1; | ||||
| 	out[n2++] |= ch; | ||||
| 	} | ||||
|     return n2; | ||||
|     } | ||||
| 
 | ||||
| unsigned char *hex2bin_m(const char *in, long *plen) | ||||
| 	{ | ||||
| 	unsigned char *p; | ||||
| 	p = OPENSSL_malloc((strlen(in) + 1)/2); | ||||
| 	*plen = hex2bin(in, p); | ||||
| 	return p; | ||||
| 	} | ||||
| 
 | ||||
| int do_hex2bn(BIGNUM **pr, const char *in) | ||||
| 	{ | ||||
| 	unsigned char *p; | ||||
| 	long plen; | ||||
| 	int r = 0; | ||||
| 	p = hex2bin_m(in, &plen); | ||||
| 	if (!p) | ||||
| 		return 0; | ||||
| 	if (!*pr) | ||||
| 		*pr = BN_new(); | ||||
| 	if (!*pr) | ||||
| 		return 0; | ||||
| 	if (BN_bin2bn(p, plen, *pr)) | ||||
| 		r = 1; | ||||
| 	OPENSSL_free(p); | ||||
| 	return r; | ||||
| 	} | ||||
| 
 | ||||
| int do_bn_print(FILE *out, BIGNUM *bn) | ||||
| 	{ | ||||
| 	int len, i; | ||||
| 	unsigned char *tmp; | ||||
| 	len = BN_num_bytes(bn); | ||||
| 	if (len == 0) | ||||
| 		{ | ||||
| 		fputs("00", out); | ||||
| 		return 1; | ||||
| 		} | ||||
| 
 | ||||
| 	tmp = OPENSSL_malloc(len); | ||||
| 	if (!tmp) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Memory allocation error\n"); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	BN_bn2bin(bn, tmp); | ||||
| 	for (i = 0; i < len; i++) | ||||
| 		fprintf(out, "%02x", tmp[i]); | ||||
| 	OPENSSL_free(tmp); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| int do_bn_print_name(FILE *out, const char *name, BIGNUM *bn) | ||||
| 	{ | ||||
| 	int r; | ||||
| 	fprintf(out, "%s = ", name); | ||||
| 	r = do_bn_print(out, bn); | ||||
| 	if (!r) | ||||
| 		return 0; | ||||
| 	fputs("\n", out); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| int parse_line(char **pkw, char **pval, char *linebuf, char *olinebuf) | ||||
| 	{ | ||||
| 	char *keyword, *value, *p, *q; | ||||
| 	strcpy(linebuf, olinebuf); | ||||
| 	keyword = linebuf; | ||||
| 	/* Skip leading space */ | ||||
| 	while (isspace((unsigned char)*keyword)) | ||||
| 		keyword++; | ||||
| 
 | ||||
| 	/* Look for = sign */ | ||||
| 	p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 	/* If no '=' exit */ | ||||
| 	if (!p) | ||||
| 		return 0; | ||||
| 
 | ||||
| 	q = p - 1; | ||||
| 
 | ||||
| 	/* Remove trailing space */ | ||||
| 	while (isspace((unsigned char)*q)) | ||||
| 		*q-- = 0; | ||||
| 
 | ||||
| 	*p = 0; | ||||
| 	value = p + 1; | ||||
| 
 | ||||
| 	/* Remove leading space from value */ | ||||
| 	while (isspace((unsigned char)*value)) | ||||
| 		value++; | ||||
| 
 | ||||
| 	/* Remove trailing space from value */ | ||||
| 	p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 	while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 		*p-- = 0; | ||||
| 
 | ||||
| 	*pkw = keyword; | ||||
| 	*pval = value; | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| BIGNUM *hex2bn(const char *in) | ||||
|     { | ||||
|     BIGNUM *p=NULL; | ||||
| 
 | ||||
|     if (!do_hex2bn(&p, in)) | ||||
| 	return NULL; | ||||
| 
 | ||||
|     return p; | ||||
|     } | ||||
| 
 | ||||
| int bin2hex(const unsigned char *in,int len,char *out) | ||||
|     { | ||||
|     int n1, n2; | ||||
|     unsigned char ch; | ||||
| 
 | ||||
|     for (n1=0,n2=0 ; n1 < len ; ++n1) | ||||
| 	{ | ||||
| 	ch=in[n1] >> 4; | ||||
| 	if (ch <= 0x09) | ||||
| 	    out[n2++]=ch+'0'; | ||||
| 	else | ||||
| 	    out[n2++]=ch-10+'a'; | ||||
| 	ch=in[n1] & 0x0f; | ||||
| 	if(ch <= 0x09) | ||||
| 	    out[n2++]=ch+'0'; | ||||
| 	else | ||||
| 	    out[n2++]=ch-10+'a'; | ||||
| 	} | ||||
|     out[n2]='\0'; | ||||
|     return n2; | ||||
|     } | ||||
| 
 | ||||
| void pv(const char *tag,const unsigned char *val,int len) | ||||
|     { | ||||
|     char obuf[2048]; | ||||
| 
 | ||||
|     bin2hex(val,len,obuf); | ||||
|     printf("%s = %s\n",tag,obuf); | ||||
|     } | ||||
| 
 | ||||
| /* To avoid extensive changes to test program at this stage just convert
 | ||||
|  * the input line into an acceptable form. Keyword lines converted to form | ||||
|  * "keyword = value\n" no matter what white space present, all other lines | ||||
|  * just have leading and trailing space removed. | ||||
|  */ | ||||
| 
 | ||||
| int tidy_line(char *linebuf, char *olinebuf) | ||||
| 	{ | ||||
| 	char *keyword, *value, *p, *q; | ||||
| 	strcpy(linebuf, olinebuf); | ||||
| 	keyword = linebuf; | ||||
| 	/* Skip leading space */ | ||||
| 	while (isspace((unsigned char)*keyword)) | ||||
| 		keyword++; | ||||
| 	/* Look for = sign */ | ||||
| 	p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 	/* If no '=' just chop leading, trailing ws */ | ||||
| 	if (!p) | ||||
| 		{ | ||||
| 		p = keyword + strlen(keyword) - 1; | ||||
| 		while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 			*p-- = 0; | ||||
| 		strcpy(olinebuf, keyword); | ||||
| 		strcat(olinebuf, "\n"); | ||||
| 		return 1; | ||||
| 		} | ||||
| 
 | ||||
| 	q = p - 1; | ||||
| 
 | ||||
| 	/* Remove trailing space */ | ||||
| 	while (isspace((unsigned char)*q)) | ||||
| 		*q-- = 0; | ||||
| 
 | ||||
| 	*p = 0; | ||||
| 	value = p + 1; | ||||
| 
 | ||||
| 	/* Remove leading space from value */ | ||||
| 	while (isspace((unsigned char)*value)) | ||||
| 		value++; | ||||
| 
 | ||||
| 	/* Remove trailing space from value */ | ||||
| 	p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 	while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 		*p-- = 0; | ||||
| 
 | ||||
| 	strcpy(olinebuf, keyword); | ||||
| 	strcat(olinebuf, " = "); | ||||
| 	strcat(olinebuf, value); | ||||
| 	strcat(olinebuf, "\n"); | ||||
| 
 | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| /* NB: this return the number of _bits_ read */ | ||||
| int bint2bin(const char *in, int len, unsigned char *out) | ||||
|     { | ||||
|     int n; | ||||
| 
 | ||||
|     memset(out,0,len); | ||||
|     for(n=0 ; n < len ; ++n) | ||||
| 	if(in[n] == '1') | ||||
| 	    out[n/8]|=(0x80 >> (n%8)); | ||||
|     return len; | ||||
|     } | ||||
| 
 | ||||
| int bin2bint(const unsigned char *in,int len,char *out) | ||||
|     { | ||||
|     int n; | ||||
| 
 | ||||
|     for(n=0 ; n < len ; ++n) | ||||
| 	out[n]=(in[n/8]&(0x80 >> (n%8))) ? '1' : '0'; | ||||
|     return n; | ||||
|     } | ||||
| 
 | ||||
| /*-----------------------------------------------*/ | ||||
| 
 | ||||
| void PrintValue(char *tag, unsigned char *val, int len) | ||||
| { | ||||
| #if VERBOSE | ||||
|   char obuf[2048]; | ||||
|   int olen; | ||||
|   olen = bin2hex(val, len, obuf); | ||||
|   printf("%s = %.*s\n", tag, olen, obuf); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| void OutputValue(char *tag, unsigned char *val, int len, FILE *rfp,int bitmode) | ||||
|     { | ||||
|     char obuf[2048]; | ||||
|     int olen; | ||||
| 
 | ||||
|     if(bitmode) | ||||
| 	olen=bin2bint(val,len,obuf); | ||||
|     else | ||||
| 	olen=bin2hex(val,len,obuf); | ||||
| 
 | ||||
|     fprintf(rfp, "%s = %.*s\n", tag, olen, obuf); | ||||
| #if VERBOSE | ||||
|     printf("%s = %.*s\n", tag, olen, obuf); | ||||
| #endif | ||||
|     } | ||||
| 
 | ||||
|  | @ -0,0 +1,887 @@ | |||
| #!/usr/bin/perl -w | ||||
| # Perl utility to run or verify FIPS 140-2 CMVP algorithm tests based on the | ||||
| # pathnames of input algorithm test files actually present (the unqualified | ||||
| # file names are consistent but the pathnames are not). | ||||
| # | ||||
| 
 | ||||
| # FIPS test definitions | ||||
| # List of all the unqualified file names we expect and command lines to run | ||||
| 
 | ||||
| # DSA tests | ||||
| my @fips_dsa_test_list = ( | ||||
| 
 | ||||
|     "DSA", | ||||
| 
 | ||||
|     [ "PQGGen",  "fips_dssvs pqg" ], | ||||
|     [ "KeyPair", "fips_dssvs keypair" ], | ||||
|     [ "SigGen",  "fips_dssvs siggen" ], | ||||
|     [ "SigVer",  "fips_dssvs sigver" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| my @fips_dsa_pqgver_test_list = ( | ||||
| 
 | ||||
|     [ "PQGVer",  "fips_dssvs pqgver" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # RSA tests | ||||
| 
 | ||||
| my @fips_rsa_test_list = ( | ||||
| 
 | ||||
|     "RSA", | ||||
| 
 | ||||
|     [ "SigGen15",  "fips_rsastest" ], | ||||
|     [ "SigVer15",  "fips_rsavtest" ], | ||||
|     [ "SigVerRSA", "fips_rsavtest -x931" ], | ||||
|     [ "KeyGenRSA", "fips_rsagtest" ], | ||||
|     [ "SigGenRSA", "fips_rsastest -x931" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # Special cases for PSS. The filename itself is | ||||
| # not sufficient to determine the test. Addditionally we | ||||
| # need to examine the file contents to determine the salt length | ||||
| # In these cases the test filename has (saltlen) appended. | ||||
| 
 | ||||
| # RSA PSS salt length 0 tests | ||||
| 
 | ||||
| my @fips_rsa_pss0_test_list = ( | ||||
| 
 | ||||
|     [ "SigGenPSS(0)", "fips_rsastest -saltlen 0" ], | ||||
|     [ "SigVerPSS(0)", "fips_rsavtest -saltlen 0" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # RSA PSS salt length 62 tests | ||||
| 
 | ||||
| my @fips_rsa_pss62_test_list = ( | ||||
|     [ "SigGenPSS(62)", "fips_rsastest -saltlen 62" ], | ||||
|     [ "SigVerPSS(62)", "fips_rsavtest -saltlen 62" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # SHA tests | ||||
| 
 | ||||
| my @fips_sha_test_list = ( | ||||
| 
 | ||||
|     "SHA", | ||||
| 
 | ||||
|     [ "SHA1LongMsg",    "fips_shatest" ], | ||||
|     [ "SHA1Monte",      "fips_shatest" ], | ||||
|     [ "SHA1ShortMsg",   "fips_shatest" ], | ||||
|     [ "SHA224LongMsg",  "fips_shatest" ], | ||||
|     [ "SHA224Monte",    "fips_shatest" ], | ||||
|     [ "SHA224ShortMsg", "fips_shatest" ], | ||||
|     [ "SHA256LongMsg",  "fips_shatest" ], | ||||
|     [ "SHA256Monte",    "fips_shatest" ], | ||||
|     [ "SHA256ShortMsg", "fips_shatest" ], | ||||
|     [ "SHA384LongMsg",  "fips_shatest" ], | ||||
|     [ "SHA384Monte",    "fips_shatest" ], | ||||
|     [ "SHA384ShortMsg", "fips_shatest" ], | ||||
|     [ "SHA512LongMsg",  "fips_shatest" ], | ||||
|     [ "SHA512Monte",    "fips_shatest" ], | ||||
|     [ "SHA512ShortMsg", "fips_shatest" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # HMAC | ||||
| 
 | ||||
| my @fips_hmac_test_list = ( | ||||
| 
 | ||||
|     "HMAC", | ||||
| 
 | ||||
|     [ "HMAC", "fips_hmactest" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # RAND tests, AES version | ||||
| 
 | ||||
| my @fips_rand_aes_test_list = ( | ||||
| 
 | ||||
|     "RAND (AES)", | ||||
| 
 | ||||
|     [ "ANSI931_AES128MCT", "fips_rngvs mct" ], | ||||
|     [ "ANSI931_AES192MCT", "fips_rngvs mct" ], | ||||
|     [ "ANSI931_AES256MCT", "fips_rngvs mct" ], | ||||
|     [ "ANSI931_AES128VST", "fips_rngvs vst" ], | ||||
|     [ "ANSI931_AES192VST", "fips_rngvs vst" ], | ||||
|     [ "ANSI931_AES256VST", "fips_rngvs vst" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # RAND tests, DES2 version | ||||
| 
 | ||||
| my @fips_rand_des2_test_list = ( | ||||
| 
 | ||||
|     "RAND (DES2)", | ||||
| 
 | ||||
|     [ "ANSI931_TDES2MCT", "fips_rngvs mct" ], | ||||
|     [ "ANSI931_TDES2VST", "fips_rngvs vst" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # AES tests | ||||
| 
 | ||||
| my @fips_aes_test_list = ( | ||||
| 
 | ||||
|     "AES", | ||||
| 
 | ||||
|     [ "CBCGFSbox128",     "fips_aesavs -f" ], | ||||
|     [ "CBCGFSbox192",     "fips_aesavs -f" ], | ||||
|     [ "CBCGFSbox256",     "fips_aesavs -f" ], | ||||
|     [ "CBCKeySbox128",    "fips_aesavs -f" ], | ||||
|     [ "CBCKeySbox192",    "fips_aesavs -f" ], | ||||
|     [ "CBCKeySbox256",    "fips_aesavs -f" ], | ||||
|     [ "CBCMCT128",        "fips_aesavs -f" ], | ||||
|     [ "CBCMCT192",        "fips_aesavs -f" ], | ||||
|     [ "CBCMCT256",        "fips_aesavs -f" ], | ||||
|     [ "CBCMMT128",        "fips_aesavs -f" ], | ||||
|     [ "CBCMMT192",        "fips_aesavs -f" ], | ||||
|     [ "CBCMMT256",        "fips_aesavs -f" ], | ||||
|     [ "CBCVarKey128",     "fips_aesavs -f" ], | ||||
|     [ "CBCVarKey192",     "fips_aesavs -f" ], | ||||
|     [ "CBCVarKey256",     "fips_aesavs -f" ], | ||||
|     [ "CBCVarTxt128",     "fips_aesavs -f" ], | ||||
|     [ "CBCVarTxt192",     "fips_aesavs -f" ], | ||||
|     [ "CBCVarTxt256",     "fips_aesavs -f" ], | ||||
|     [ "CFB128GFSbox128",  "fips_aesavs -f" ], | ||||
|     [ "CFB128GFSbox192",  "fips_aesavs -f" ], | ||||
|     [ "CFB128GFSbox256",  "fips_aesavs -f" ], | ||||
|     [ "CFB128KeySbox128", "fips_aesavs -f" ], | ||||
|     [ "CFB128KeySbox192", "fips_aesavs -f" ], | ||||
|     [ "CFB128KeySbox256", "fips_aesavs -f" ], | ||||
|     [ "CFB128MCT128",     "fips_aesavs -f" ], | ||||
|     [ "CFB128MCT192",     "fips_aesavs -f" ], | ||||
|     [ "CFB128MCT256",     "fips_aesavs -f" ], | ||||
|     [ "CFB128MMT128",     "fips_aesavs -f" ], | ||||
|     [ "CFB128MMT192",     "fips_aesavs -f" ], | ||||
|     [ "CFB128MMT256",     "fips_aesavs -f" ], | ||||
|     [ "CFB128VarKey128",  "fips_aesavs -f" ], | ||||
|     [ "CFB128VarKey192",  "fips_aesavs -f" ], | ||||
|     [ "CFB128VarKey256",  "fips_aesavs -f" ], | ||||
|     [ "CFB128VarTxt128",  "fips_aesavs -f" ], | ||||
|     [ "CFB128VarTxt192",  "fips_aesavs -f" ], | ||||
|     [ "CFB128VarTxt256",  "fips_aesavs -f" ], | ||||
|     [ "CFB8GFSbox128",    "fips_aesavs -f" ], | ||||
|     [ "CFB8GFSbox192",    "fips_aesavs -f" ], | ||||
|     [ "CFB8GFSbox256",    "fips_aesavs -f" ], | ||||
|     [ "CFB8KeySbox128",   "fips_aesavs -f" ], | ||||
|     [ "CFB8KeySbox192",   "fips_aesavs -f" ], | ||||
|     [ "CFB8KeySbox256",   "fips_aesavs -f" ], | ||||
|     [ "CFB8MCT128",       "fips_aesavs -f" ], | ||||
|     [ "CFB8MCT192",       "fips_aesavs -f" ], | ||||
|     [ "CFB8MCT256",       "fips_aesavs -f" ], | ||||
|     [ "CFB8MMT128",       "fips_aesavs -f" ], | ||||
|     [ "CFB8MMT192",       "fips_aesavs -f" ], | ||||
|     [ "CFB8MMT256",       "fips_aesavs -f" ], | ||||
|     [ "CFB8VarKey128",    "fips_aesavs -f" ], | ||||
|     [ "CFB8VarKey192",    "fips_aesavs -f" ], | ||||
|     [ "CFB8VarKey256",    "fips_aesavs -f" ], | ||||
|     [ "CFB8VarTxt128",    "fips_aesavs -f" ], | ||||
|     [ "CFB8VarTxt192",    "fips_aesavs -f" ], | ||||
|     [ "CFB8VarTxt256",    "fips_aesavs -f" ], | ||||
| 
 | ||||
|     [ "ECBGFSbox128",  "fips_aesavs -f" ], | ||||
|     [ "ECBGFSbox192",  "fips_aesavs -f" ], | ||||
|     [ "ECBGFSbox256",  "fips_aesavs -f" ], | ||||
|     [ "ECBKeySbox128", "fips_aesavs -f" ], | ||||
|     [ "ECBKeySbox192", "fips_aesavs -f" ], | ||||
|     [ "ECBKeySbox256", "fips_aesavs -f" ], | ||||
|     [ "ECBMCT128",     "fips_aesavs -f" ], | ||||
|     [ "ECBMCT192",     "fips_aesavs -f" ], | ||||
|     [ "ECBMCT256",     "fips_aesavs -f" ], | ||||
|     [ "ECBMMT128",     "fips_aesavs -f" ], | ||||
|     [ "ECBMMT192",     "fips_aesavs -f" ], | ||||
|     [ "ECBMMT256",     "fips_aesavs -f" ], | ||||
|     [ "ECBVarKey128",  "fips_aesavs -f" ], | ||||
|     [ "ECBVarKey192",  "fips_aesavs -f" ], | ||||
|     [ "ECBVarKey256",  "fips_aesavs -f" ], | ||||
|     [ "ECBVarTxt128",  "fips_aesavs -f" ], | ||||
|     [ "ECBVarTxt192",  "fips_aesavs -f" ], | ||||
|     [ "ECBVarTxt256",  "fips_aesavs -f" ], | ||||
|     [ "OFBGFSbox128",  "fips_aesavs -f" ], | ||||
|     [ "OFBGFSbox192",  "fips_aesavs -f" ], | ||||
|     [ "OFBGFSbox256",  "fips_aesavs -f" ], | ||||
|     [ "OFBKeySbox128", "fips_aesavs -f" ], | ||||
|     [ "OFBKeySbox192", "fips_aesavs -f" ], | ||||
|     [ "OFBKeySbox256", "fips_aesavs -f" ], | ||||
|     [ "OFBMCT128",     "fips_aesavs -f" ], | ||||
|     [ "OFBMCT192",     "fips_aesavs -f" ], | ||||
|     [ "OFBMCT256",     "fips_aesavs -f" ], | ||||
|     [ "OFBMMT128",     "fips_aesavs -f" ], | ||||
|     [ "OFBMMT192",     "fips_aesavs -f" ], | ||||
|     [ "OFBMMT256",     "fips_aesavs -f" ], | ||||
|     [ "OFBVarKey128",  "fips_aesavs -f" ], | ||||
|     [ "OFBVarKey192",  "fips_aesavs -f" ], | ||||
|     [ "OFBVarKey256",  "fips_aesavs -f" ], | ||||
|     [ "OFBVarTxt128",  "fips_aesavs -f" ], | ||||
|     [ "OFBVarTxt192",  "fips_aesavs -f" ], | ||||
|     [ "OFBVarTxt256",  "fips_aesavs -f" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| my @fips_aes_cfb1_test_list = ( | ||||
| 
 | ||||
|     # AES CFB1 tests | ||||
| 
 | ||||
|     [ "CFB1GFSbox128",  "fips_aesavs -f" ], | ||||
|     [ "CFB1GFSbox192",  "fips_aesavs -f" ], | ||||
|     [ "CFB1GFSbox256",  "fips_aesavs -f" ], | ||||
|     [ "CFB1KeySbox128", "fips_aesavs -f" ], | ||||
|     [ "CFB1KeySbox192", "fips_aesavs -f" ], | ||||
|     [ "CFB1KeySbox256", "fips_aesavs -f" ], | ||||
|     [ "CFB1MCT128",     "fips_aesavs -f" ], | ||||
|     [ "CFB1MCT192",     "fips_aesavs -f" ], | ||||
|     [ "CFB1MCT256",     "fips_aesavs -f" ], | ||||
|     [ "CFB1MMT128",     "fips_aesavs -f" ], | ||||
|     [ "CFB1MMT192",     "fips_aesavs -f" ], | ||||
|     [ "CFB1MMT256",     "fips_aesavs -f" ], | ||||
|     [ "CFB1VarKey128",  "fips_aesavs -f" ], | ||||
|     [ "CFB1VarKey192",  "fips_aesavs -f" ], | ||||
|     [ "CFB1VarKey256",  "fips_aesavs -f" ], | ||||
|     [ "CFB1VarTxt128",  "fips_aesavs -f" ], | ||||
|     [ "CFB1VarTxt192",  "fips_aesavs -f" ], | ||||
|     [ "CFB1VarTxt256",  "fips_aesavs -f" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # Triple DES tests | ||||
| 
 | ||||
| my @fips_des3_test_list = ( | ||||
| 
 | ||||
|     "Triple DES", | ||||
| 
 | ||||
|     [ "TCBCinvperm",   "fips_desmovs -f" ], | ||||
|     [ "TCBCMMT1",      "fips_desmovs -f" ], | ||||
|     [ "TCBCMMT2",      "fips_desmovs -f" ], | ||||
|     [ "TCBCMMT3",      "fips_desmovs -f" ], | ||||
|     [ "TCBCMonte1",    "fips_desmovs -f" ], | ||||
|     [ "TCBCMonte2",    "fips_desmovs -f" ], | ||||
|     [ "TCBCMonte3",    "fips_desmovs -f" ], | ||||
|     [ "TCBCpermop",    "fips_desmovs -f" ], | ||||
|     [ "TCBCsubtab",    "fips_desmovs -f" ], | ||||
|     [ "TCBCvarkey",    "fips_desmovs -f" ], | ||||
|     [ "TCBCvartext",   "fips_desmovs -f" ], | ||||
|     [ "TCFB64invperm", "fips_desmovs -f" ], | ||||
|     [ "TCFB64MMT1",    "fips_desmovs -f" ], | ||||
|     [ "TCFB64MMT2",    "fips_desmovs -f" ], | ||||
|     [ "TCFB64MMT3",    "fips_desmovs -f" ], | ||||
|     [ "TCFB64Monte1",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64Monte2",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64Monte3",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64permop",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64subtab",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64varkey",  "fips_desmovs -f" ], | ||||
|     [ "TCFB64vartext", "fips_desmovs -f" ], | ||||
|     [ "TCFB8invperm",  "fips_desmovs -f" ], | ||||
|     [ "TCFB8MMT1",     "fips_desmovs -f" ], | ||||
|     [ "TCFB8MMT2",     "fips_desmovs -f" ], | ||||
|     [ "TCFB8MMT3",     "fips_desmovs -f" ], | ||||
|     [ "TCFB8Monte1",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8Monte2",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8Monte3",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8permop",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8subtab",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8varkey",   "fips_desmovs -f" ], | ||||
|     [ "TCFB8vartext",  "fips_desmovs -f" ], | ||||
|     [ "TECBinvperm",   "fips_desmovs -f" ], | ||||
|     [ "TECBMMT1",      "fips_desmovs -f" ], | ||||
|     [ "TECBMMT2",      "fips_desmovs -f" ], | ||||
|     [ "TECBMMT3",      "fips_desmovs -f" ], | ||||
|     [ "TECBMonte1",    "fips_desmovs -f" ], | ||||
|     [ "TECBMonte2",    "fips_desmovs -f" ], | ||||
|     [ "TECBMonte3",    "fips_desmovs -f" ], | ||||
|     [ "TECBpermop",    "fips_desmovs -f" ], | ||||
|     [ "TECBsubtab",    "fips_desmovs -f" ], | ||||
|     [ "TECBvarkey",    "fips_desmovs -f" ], | ||||
|     [ "TECBvartext",   "fips_desmovs -f" ], | ||||
|     [ "TOFBinvperm",   "fips_desmovs -f" ], | ||||
|     [ "TOFBMMT1",      "fips_desmovs -f" ], | ||||
|     [ "TOFBMMT2",      "fips_desmovs -f" ], | ||||
|     [ "TOFBMMT3",      "fips_desmovs -f" ], | ||||
|     [ "TOFBMonte1",    "fips_desmovs -f" ], | ||||
|     [ "TOFBMonte2",    "fips_desmovs -f" ], | ||||
|     [ "TOFBMonte3",    "fips_desmovs -f" ], | ||||
|     [ "TOFBpermop",    "fips_desmovs -f" ], | ||||
|     [ "TOFBsubtab",    "fips_desmovs -f" ], | ||||
|     [ "TOFBvarkey",    "fips_desmovs -f" ], | ||||
|     [ "TOFBvartext",   "fips_desmovs -f" ] | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| my @fips_des3_cfb1_test_list = ( | ||||
| 
 | ||||
|     # DES3 CFB1 tests | ||||
| 
 | ||||
|     [ "TCFB1invperm",  "fips_desmovs -f" ], | ||||
|     [ "TCFB1MMT1",     "fips_desmovs -f" ], | ||||
|     [ "TCFB1MMT2",     "fips_desmovs -f" ], | ||||
|     [ "TCFB1MMT3",     "fips_desmovs -f" ], | ||||
|     [ "TCFB1Monte1",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1Monte2",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1Monte3",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1permop",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1subtab",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1varkey",   "fips_desmovs -f" ], | ||||
|     [ "TCFB1vartext",  "fips_desmovs -f" ], | ||||
| 
 | ||||
| ); | ||||
| 
 | ||||
| # Verification special cases. | ||||
| # In most cases the output of a test is deterministic and | ||||
| # it can be compared to a known good result. A few involve | ||||
| # the genration and use of random keys and the output will | ||||
| # be different each time. In thoses cases we perform special tests | ||||
| # to simply check their consistency. For example signature generation | ||||
| # output will be run through signature verification to see if all outputs | ||||
| # show as valid. | ||||
| # | ||||
| 
 | ||||
| my %verify_special = ( | ||||
|     "PQGGen"        => "fips_dssvs pqgver", | ||||
|     "KeyPair"       => "fips_dssvs keyver", | ||||
|     "SigGen"        => "fips_dssvs sigver", | ||||
|     "SigGen15"      => "fips_rsavtest", | ||||
|     "SigGenRSA"     => "fips_rsavtest -x931", | ||||
|     "SigGenPSS(0)"  => "fips_rsavtest -saltlen 0", | ||||
|     "SigGenPSS(62)" => "fips_rsavtest -saltlen 62", | ||||
| ); | ||||
| 
 | ||||
| my $win32  = $^O =~ m/mswin/i; | ||||
| my $onedir = 0; | ||||
| my $filter = ""; | ||||
| my $tvdir; | ||||
| my $tprefix; | ||||
| my $shwrap_prefix; | ||||
| my $debug          = 0; | ||||
| my $quiet          = 0; | ||||
| my $notest         = 0; | ||||
| my $verify         = 1; | ||||
| my $rspdir         = "rsp"; | ||||
| my $ignore_missing = 0; | ||||
| my $ignore_bogus   = 0; | ||||
| my $bufout         = ''; | ||||
| my $list_tests     = 0; | ||||
| 
 | ||||
| my %fips_enabled = ( | ||||
|     dsa         => 1, | ||||
|     "dsa-pqgver"  => 0, | ||||
|     rsa         => 1, | ||||
|     "rsa-pss0"  => 0, | ||||
|     "rsa-pss62" => 1, | ||||
|     sha         => 1, | ||||
|     hmac        => 1, | ||||
|     "rand-aes"  => 1, | ||||
|     "rand-des2" => 0, | ||||
|     aes         => 1, | ||||
|     "aes-cfb1"  => 0, | ||||
|     des3        => 1, | ||||
|     "des3-cfb1" => 0 | ||||
| ); | ||||
| 
 | ||||
| foreach (@ARGV) { | ||||
|     if ( $_ eq "--win32" ) { | ||||
|         $win32 = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--onedir" ) { | ||||
|         $onedir = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--debug" ) { | ||||
|         $debug = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--ignore-missing" ) { | ||||
|         $ignore_missing = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--ignore-bogus" ) { | ||||
|         $ignore_bogus = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--generate" ) { | ||||
|         $verify = 0; | ||||
|     } | ||||
|     elsif ( $_ eq "--notest" ) { | ||||
|         $notest = 1; | ||||
|     } | ||||
|     elsif ( $_ eq "--quiet" ) { | ||||
|         $quiet = 1; | ||||
|     } | ||||
|     elsif (/--dir=(.*)$/) { | ||||
|         $tvdir = $1; | ||||
|     } | ||||
|     elsif (/--rspdir=(.*)$/) { | ||||
|         $rspdir = $1; | ||||
|     } | ||||
|     elsif (/--tprefix=(.*)$/) { | ||||
|         $tprefix = $1; | ||||
|     } | ||||
|     elsif (/--shwrap_prefix=(.*)$/) { | ||||
|         $shwrap_prefix = $1; | ||||
|     } | ||||
|     elsif (/^--(enable|disable)-(.*)$/) { | ||||
|         if ( !exists $fips_enabled{$2} ) { | ||||
|             print STDERR "Unknown test $2\n"; | ||||
|         } | ||||
|         if ( $1 eq "enable" ) { | ||||
|             $fips_enabled{$2} = 1; | ||||
|         } | ||||
|         else { | ||||
|             $fips_enabled{$2} = 0; | ||||
|         } | ||||
|     } | ||||
|     elsif (/--filter=(.*)$/) { | ||||
|         $filter = $1; | ||||
|     } | ||||
|     elsif (/^--list-tests$/) { | ||||
|         $list_tests = 1; | ||||
|     } | ||||
|     else { | ||||
|         Help(); | ||||
|         exit(1); | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| my @fips_test_list; | ||||
| 
 | ||||
| push @fips_test_list, @fips_dsa_test_list       if $fips_enabled{"dsa"}; | ||||
| push @fips_test_list, @fips_dsa_pqgver_test_list if $fips_enabled{"dsa-pqgver"}; | ||||
| push @fips_test_list, @fips_rsa_test_list       if $fips_enabled{"rsa"}; | ||||
| push @fips_test_list, @fips_rsa_pss0_test_list  if $fips_enabled{"rsa-pss0"}; | ||||
| push @fips_test_list, @fips_rsa_pss62_test_list if $fips_enabled{"rsa-pss62"}; | ||||
| push @fips_test_list, @fips_sha_test_list       if $fips_enabled{"sha"}; | ||||
| push @fips_test_list, @fips_hmac_test_list      if $fips_enabled{"hmac"}; | ||||
| push @fips_test_list, @fips_rand_aes_test_list  if $fips_enabled{"rand-aes"}; | ||||
| push @fips_test_list, @fips_rand_des2_test_list if $fips_enabled{"rand-des2"}; | ||||
| push @fips_test_list, @fips_aes_test_list       if $fips_enabled{"aes"}; | ||||
| push @fips_test_list, @fips_aes_cfb1_test_list  if $fips_enabled{"aes-cfb1"}; | ||||
| push @fips_test_list, @fips_des3_test_list      if $fips_enabled{"des3"}; | ||||
| push @fips_test_list, @fips_des3_cfb1_test_list if $fips_enabled{"des3-cfb1"}; | ||||
| 
 | ||||
| if ($list_tests) { | ||||
|     my ( $test, $en ); | ||||
|     print "=====TEST LIST=====\n"; | ||||
|     foreach $test ( sort keys %fips_enabled ) { | ||||
|         $en = $fips_enabled{$test}; | ||||
|         $test =~ tr/[a-z]/[A-Z]/; | ||||
|         printf "%-10s %s\n", $test, $en ? "enabled" : "disabled"; | ||||
|     } | ||||
|     exit(0); | ||||
| } | ||||
| 
 | ||||
| foreach (@fips_test_list) { | ||||
|     next unless ref($_); | ||||
|     my $nm = $_->[0]; | ||||
|     $_->[2] = ""; | ||||
|     $_->[3] = ""; | ||||
|     print STDERR "Duplicate test $nm\n" if exists $fips_tests{$nm}; | ||||
|     $fips_tests{$nm} = $_; | ||||
| } | ||||
| 
 | ||||
| $tvdir = "." unless defined $tvdir; | ||||
| 
 | ||||
| if ($win32) { | ||||
|     if ( !defined $tprefix ) { | ||||
|         if ($onedir) { | ||||
|             $tprefix = ".\\"; | ||||
|         } | ||||
|         else { | ||||
|             $tprefix = "..\\out32dll\\"; | ||||
|         } | ||||
|     } | ||||
| } | ||||
| else { | ||||
|     if ($onedir) { | ||||
|         $tprefix       = "./" unless defined $tprefix; | ||||
|         $shwrap_prefix = "./" unless defined $shwrap_prefix; | ||||
|     } | ||||
|     else { | ||||
|         $tprefix       = "../test/" unless defined $tprefix; | ||||
|         $shwrap_prefix = "../util/" unless defined $shwrap_prefix; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| sanity_check_exe( $win32, $tprefix, $shwrap_prefix ); | ||||
| 
 | ||||
| my $cmd_prefix = $win32 ? "" : "${shwrap_prefix}shlib_wrap.sh "; | ||||
| 
 | ||||
| find_files( $filter, $tvdir ); | ||||
| 
 | ||||
| sanity_check_files(); | ||||
| 
 | ||||
| my ( $runerr, $cmperr, $cmpok, $scheckrunerr, $scheckerr, $scheckok, $skipcnt ) | ||||
|   = ( 0, 0, 0, 0, 0, 0, 0 ); | ||||
| 
 | ||||
| exit(0) if $notest; | ||||
| 
 | ||||
| run_tests( $verify, $win32, $tprefix, $filter, $tvdir ); | ||||
| 
 | ||||
| if ($verify) { | ||||
|     print "ALGORITHM TEST VERIFY SUMMARY REPORT:\n"; | ||||
|     print "Tests skipped due to missing files:        $skipcnt\n"; | ||||
|     print "Algorithm test program execution failures: $runerr\n"; | ||||
|     print "Test comparisons successful:               $cmpok\n"; | ||||
|     print "Test comparisons failed:                   $cmperr\n"; | ||||
|     print "Test sanity checks successful:             $scheckok\n"; | ||||
|     print "Test sanity checks failed:                 $scheckerr\n"; | ||||
|     print "Sanity check program execution failures:   $scheckrunerr\n"; | ||||
| 
 | ||||
|     if ( $runerr || $cmperr || $scheckrunerr || $scheckerr ) { | ||||
|         print "***TEST FAILURE***\n"; | ||||
|     } | ||||
|     else { | ||||
|         print "***ALL TESTS SUCCESSFUL***\n"; | ||||
|     } | ||||
| } | ||||
| else { | ||||
|     print "ALGORITHM TEST SUMMARY REPORT:\n"; | ||||
|     print "Tests skipped due to missing files:        $skipcnt\n"; | ||||
|     print "Algorithm test program execution failures: $runerr\n"; | ||||
| 
 | ||||
|     if ($runerr) { | ||||
|         print "***TEST FAILURE***\n"; | ||||
|     } | ||||
|     else { | ||||
|         print "***ALL TESTS SUCCESSFUL***\n"; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub Help { | ||||
|     ( my $cmd ) = ( $0 =~ m#([^/]+)$# ); | ||||
|     print <<EOF; | ||||
| $cmd: generate run CMVP algorithm tests | ||||
| 	--debug                     Enable debug output | ||||
| 	--dir=<dirname>             Optional root for *.req file search | ||||
| 	--filter=<regexp> | ||||
| 	--onedir <dirname>          Assume all components in current directory | ||||
| 	--rspdir=<dirname>          Name of subdirectories containing *.rsp files, default "rsp" | ||||
| 	--shwrap_prefix=<prefix> | ||||
| 	--tprefix=<prefix> | ||||
| 	--ignore-bogus              Ignore duplicate or bogus files | ||||
| 	--ignore-missing            Ignore missing test files | ||||
| 	--quiet                     Shhh.... | ||||
| 	--generate                  Generate algorithm test output | ||||
| 	--win32                     Win32 environment | ||||
| 	--enable-<alg>		    Enable algorithm set <alg>. | ||||
| 	--disable-<alg>		    Disable algorithm set <alg>. | ||||
| 	Where <alg> can be one of: | ||||
| EOF | ||||
| 
 | ||||
| while (my ($key, $value) = each %fips_enabled) | ||||
| 	{ | ||||
| 	printf "\t\t%-20s(%s by default)\n", $key , | ||||
| 			$value ? "enabled" : "disabled"; | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| # Sanity check to see if all necessary executables exist | ||||
| 
 | ||||
| sub sanity_check_exe { | ||||
|     my ( $win32, $tprefix, $shwrap_prefix ) = @_; | ||||
|     my %exe_list; | ||||
|     my $bad = 0; | ||||
|     $exe_list{ $shwrap_prefix . "shlib_wrap.sh" } = 1 unless $win32; | ||||
|     foreach (@fips_test_list) { | ||||
|         next unless ref($_); | ||||
|         my $cmd = $_->[1]; | ||||
|         $cmd =~ s/ .*$//; | ||||
|         $cmd = $tprefix . $cmd; | ||||
|         $cmd .= ".exe" if $win32; | ||||
|         $exe_list{$cmd} = 1; | ||||
|     } | ||||
| 
 | ||||
|     foreach ( sort keys %exe_list ) { | ||||
|         if ( !-f $_ ) { | ||||
|             print STDERR "ERROR: can't find executable $_\n"; | ||||
|             $bad = 1; | ||||
|         } | ||||
|     } | ||||
|     if ($bad) { | ||||
|         print STDERR "FATAL ERROR: executables missing\n"; | ||||
|         exit(1); | ||||
|     } | ||||
|     elsif ($debug) { | ||||
|         print STDERR "Executable sanity check passed OK\n"; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| # Search for all request and response files | ||||
| 
 | ||||
| sub find_files { | ||||
|     my ( $filter, $dir ) = @_; | ||||
|     my ( $dirh, $testname ); | ||||
|     opendir( $dirh, $dir ); | ||||
|     while ( $_ = readdir($dirh) ) { | ||||
|         next if ( $_ eq "." || $_ eq ".." ); | ||||
|         $_ = "$dir/$_"; | ||||
|         if ( -f "$_" ) { | ||||
|             if (/\/([^\/]*)\.rsp$/) { | ||||
|                 $testname = fix_pss( $1, $_ ); | ||||
|                 if ( exists $fips_tests{$testname} ) { | ||||
|                     if ( $fips_tests{$testname}->[3] eq "" ) { | ||||
|                         $fips_tests{$testname}->[3] = $_; | ||||
|                     } | ||||
|                     else { | ||||
|                         print STDERR | ||||
| "WARNING: duplicate response file $_ for test $testname\n"; | ||||
|                         $nbogus++; | ||||
|                     } | ||||
|                 } | ||||
|                 else { | ||||
|                     print STDERR "WARNING: bogus file $_\n"; | ||||
|                     $nbogus++; | ||||
|                 } | ||||
|             } | ||||
|             next unless /$filter.*\.req$/i; | ||||
|             if (/\/([^\/]*)\.req$/) { | ||||
|                 $testname = fix_pss( $1, $_ ); | ||||
|                 if ( exists $fips_tests{$testname} ) { | ||||
|                     if ( $fips_tests{$testname}->[2] eq "" ) { | ||||
|                         $fips_tests{$testname}->[2] = $_; | ||||
|                     } | ||||
|                     else { | ||||
|                         print STDERR | ||||
| "WARNING: duplicate request file $_ for test $testname\n"; | ||||
|                         $nbogus++; | ||||
|                     } | ||||
| 
 | ||||
|                 } | ||||
|                 elsif ( !/SHAmix\.req$/ ) { | ||||
|                     print STDERR "WARNING: unrecognized filename $_\n"; | ||||
|                     $nbogus++; | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
|         elsif ( -d "$_" ) { | ||||
|             find_files( $filter, $_ ); | ||||
|         } | ||||
|     } | ||||
|     closedir($dirh); | ||||
| } | ||||
| 
 | ||||
| sub fix_pss { | ||||
|     my ( $test, $path ) = @_; | ||||
|     my $sl = ""; | ||||
|     local $_; | ||||
|     if ( $test =~ /PSS/ ) { | ||||
|         open( IN, $path ) || die "Can't Open File $path"; | ||||
|         while (<IN>) { | ||||
|             if (/^\s*#\s*salt\s+len:\s+(\d+)\s*$/i) { | ||||
|                 $sl = $1; | ||||
|                 last; | ||||
|             } | ||||
|         } | ||||
|         close IN; | ||||
|         if ( $sl eq "" ) { | ||||
|             print STDERR "WARNING: No Salt length detected for file $path\n"; | ||||
|         } | ||||
|         else { | ||||
|             return $test . "($sl)"; | ||||
|         } | ||||
|     } | ||||
|     return $test; | ||||
| } | ||||
| 
 | ||||
| sub sanity_check_files { | ||||
|     my $bad = 0; | ||||
|     foreach (@fips_test_list) { | ||||
|         next unless ref($_); | ||||
|         my ( $tst, $cmd, $req, $resp ) = @$_; | ||||
| 
 | ||||
|         #print STDERR "FILES $tst, $cmd, $req, $resp\n"; | ||||
|         if ( $req eq "" ) { | ||||
|             print STDERR "WARNING: missing request file for $tst\n"; | ||||
|             $bad = 1; | ||||
|             next; | ||||
|         } | ||||
|         if ( $verify && $resp eq "" ) { | ||||
|             print STDERR "WARNING: no response file for test $tst\n"; | ||||
|             $bad = 1; | ||||
|         } | ||||
|         elsif ( !$verify && $resp ne "" ) { | ||||
|             print STDERR "WARNING: response file $resp will be overwritten\n"; | ||||
|         } | ||||
|     } | ||||
|     if ($bad) { | ||||
|         print STDERR "ERROR: test vector file set not complete\n"; | ||||
|         exit(1) unless $ignore_missing; | ||||
|     } | ||||
|     if ($nbogus) { | ||||
|         print STDERR | ||||
|           "ERROR: $nbogus bogus or duplicate request and response files\n"; | ||||
|         exit(1) unless $ignore_bogus; | ||||
|     } | ||||
|     if ( $debug && !$nbogus && !$bad ) { | ||||
|         print STDERR "test vector file set complete\n"; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| sub run_tests { | ||||
|     my ( $verify, $win32, $tprefix, $filter, $tvdir ) = @_; | ||||
|     my ( $tname, $tref ); | ||||
|     my $bad = 0; | ||||
|     foreach (@fips_test_list) { | ||||
|         if ( !ref($_) ) { | ||||
|             print "Running $_ tests\n" unless $quiet; | ||||
|             next; | ||||
|         } | ||||
|         my ( $tname, $tcmd, $req, $rsp ) = @$_; | ||||
|         my $out = $rsp; | ||||
|         if ($verify) { | ||||
|             $out =~ s/\.rsp$/.tst/; | ||||
|         } | ||||
|         if ( $req eq "" ) { | ||||
|             print STDERR | ||||
|               "WARNING: Request file for $tname missing: test skipped\n"; | ||||
|             $skipcnt++; | ||||
|             next; | ||||
|         } | ||||
|         if ( $verify && $rsp eq "" ) { | ||||
|             print STDERR | ||||
|               "WARNING: Response file for $tname missing: test skipped\n"; | ||||
|             $skipcnt++; | ||||
|             next; | ||||
|         } | ||||
|         elsif ( !$verify ) { | ||||
|             if ( $rsp ne "" ) { | ||||
|                 print STDERR "WARNING: Response file for $tname deleted\n"; | ||||
|                 unlink $rsp; | ||||
|             } | ||||
|             $out = $req; | ||||
|             $out =~ s|/req/(\S+)\.req|/$rspdir/$1.rsp|; | ||||
|             my $outdir = $out; | ||||
|             $outdir =~ s|/[^/]*$||; | ||||
|             if ( !-d $outdir ) { | ||||
|                 print STDERR "DEBUG: Creating directory $outdir\n" if $debug; | ||||
|                 mkdir($outdir) || die "Can't create directory $outdir"; | ||||
|             } | ||||
|         } | ||||
|         my $cmd = "$cmd_prefix$tprefix$tcmd "; | ||||
|         if ( $tcmd =~ /-f$/ ) { | ||||
|             $cmd .= "\"$req\" \"$out\""; | ||||
|         } | ||||
|         else { | ||||
|             $cmd .= "<\"$req\" >\"$out\""; | ||||
|         } | ||||
|         print STDERR "DEBUG: running test $tname\n" if ( $debug && !$verify ); | ||||
|         system($cmd); | ||||
|         if ( $? != 0 ) { | ||||
|             print STDERR | ||||
|               "WARNING: error executing test $tname for command: $cmd\n"; | ||||
|             $runerr++; | ||||
|             next; | ||||
|         } | ||||
|         if ($verify) { | ||||
|             if ( exists $verify_special{$tname} ) { | ||||
|                 my $vout = $rsp; | ||||
|                 $vout =~ s/\.rsp$/.ver/; | ||||
|                 $tcmd = $verify_special{$tname}; | ||||
|                 $cmd  = "$cmd_prefix$tprefix$tcmd "; | ||||
|                 $cmd .= "<\"$out\" >\"$vout\""; | ||||
|                 system($cmd); | ||||
|                 if ( $? != 0 ) { | ||||
|                     print STDERR | ||||
|                       "WARNING: error executing verify test $tname $cmd\n"; | ||||
|                     $scheckrunerr++; | ||||
|                     next; | ||||
|                 } | ||||
|                 my ( $fcount, $pcount ) = ( 0, 0 ); | ||||
|                 open VER, "$vout"; | ||||
|                 while (<VER>) { | ||||
|                     if (/^Result\s*=\s*(\S*)\s*$/i) | ||||
| 
 | ||||
|                     { | ||||
|                         if ( $1 eq "F" ) { | ||||
|                             $fcount++; | ||||
|                         } | ||||
|                         else { | ||||
|                             $pcount++; | ||||
|                         } | ||||
|                     } | ||||
|                 } | ||||
|                 close VER; | ||||
| 
 | ||||
|                 unlink $vout; | ||||
|                 if ( $fcount || $debug ) { | ||||
|                     print STDERR "DEBUG: $tname, Pass=$pcount, Fail=$fcount\n"; | ||||
|                 } | ||||
|                 if ( $fcount || !$pcount ) { | ||||
|                     $scheckerr++; | ||||
|                 } | ||||
|                 else { | ||||
|                     $scheckok++; | ||||
|                 } | ||||
| 
 | ||||
|             } | ||||
|             elsif ( !cmp_file( $tname, $rsp, $out ) ) { | ||||
|                 $cmperr++; | ||||
|             } | ||||
|             else { | ||||
|                 $cmpok++; | ||||
|             } | ||||
|             unlink $out; | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| sub cmp_file { | ||||
|     my ( $tname, $rsp, $tst ) = @_; | ||||
|     my ( $rspf,    $tstf ); | ||||
|     my ( $rspline, $tstline ); | ||||
|     if ( !open( $rspf, $rsp ) ) { | ||||
|         print STDERR "ERROR: can't open request file $rsp\n"; | ||||
|         return 0; | ||||
|     } | ||||
|     if ( !open( $tstf, $tst ) ) { | ||||
|         print STDERR "ERROR: can't open output file $tst\n"; | ||||
|         return 0; | ||||
|     } | ||||
|     for ( ; ; ) { | ||||
|         $rspline = next_line($rspf); | ||||
|         $tstline = next_line($tstf); | ||||
|         if ( !defined($rspline) && !defined($tstline) ) { | ||||
|             print STDERR "DEBUG: $tname file comparison OK\n" if $debug; | ||||
|             return 1; | ||||
|         } | ||||
|         if ( !defined($rspline) ) { | ||||
|             print STDERR "ERROR: $tname EOF on $rsp\n"; | ||||
|             return 0; | ||||
|         } | ||||
|         if ( !defined($tstline) ) { | ||||
|             print STDERR "ERROR: $tname EOF on $tst\n"; | ||||
|             return 0; | ||||
|         } | ||||
| 
 | ||||
|         # Workaround for bug in RAND des2 test output */ | ||||
|         if ( $tstline =~ /^Key2 =/ && $rspline =~ /^Key1 =/ ) { | ||||
|             $rspline =~ s/^Key1/Key2/; | ||||
|         } | ||||
| 
 | ||||
|         if ( $tstline ne $rspline ) { | ||||
|             print STDERR "ERROR: $tname mismatch:\n"; | ||||
|             print STDERR "\t \"$tstline\" != \"$rspline\"\n"; | ||||
|             return 0; | ||||
|         } | ||||
|     } | ||||
|     return 1; | ||||
| } | ||||
| 
 | ||||
| sub next_line { | ||||
|     my ($in) = @_; | ||||
| 
 | ||||
|     while (<$in>) { | ||||
|         chomp; | ||||
| 
 | ||||
|         # Delete comments | ||||
|         s/#.*$//; | ||||
| 
 | ||||
|         # Ignore blank lines | ||||
|         next if (/^\s*$/); | ||||
| 
 | ||||
|         # Translate multiple space into one | ||||
|         s/\s+/ /g; | ||||
| 	# Delete trailing whitespace | ||||
| 	s/\s+$//; | ||||
|         return $_; | ||||
|     } | ||||
|     return undef; | ||||
| } | ||||
|  | @ -0,0 +1,178 @@ | |||
| #!/bin/sh -e | ||||
| # | ||||
| # Copyright (c) 2005-2007 The OpenSSL Project. | ||||
| # | ||||
| # Depending on output file name, the script either embeds fingerprint | ||||
| # into libcrypto.so or static application. "Static" refers to static | ||||
| # libcrypto.a, not [necessarily] application per se. | ||||
| # | ||||
| # Even though this script is called fipsld, it expects C compiler | ||||
| # command line syntax and $FIPSLD_CC or $CC environment variable set | ||||
| # and can even be used to compile source files. | ||||
| 
 | ||||
| #set -x | ||||
| 
 | ||||
| CC=${FIPSLD_CC:-${CC}} | ||||
| [ -n "${CC}" ] || { echo '$CC is not defined'; exit 1; } | ||||
| 
 | ||||
| # Initially -c wasn't intended to be interpreted here, but it might | ||||
| # make life easier for those who want to build FIPS-ified applications | ||||
| # with minimal [if any] modifications to their Makefiles... | ||||
| (   while [ "x$1" != "x" -a "x$1" != "x-c" -a "x$1" != "x-E" ]; do shift; done; | ||||
|     [ $# -ge 1 ] | ||||
| ) && exec ${CC} "$@" | ||||
| 
 | ||||
| TARGET=`(while [ "x$1" != "x" -a "x$1" != "x-o" ]; do shift; done; echo $2)` | ||||
| 
 | ||||
| # If using an auto-tooled (autoconf/automake/libtool) project, | ||||
| # configure will fail when testing the compiler or even performing | ||||
| # simple checks. Pass-through to compiler directly if application is | ||||
| # is not being linked with libcrypto, allowing auto-tooled applications | ||||
| # to utilize fipsld (e.g. CC=/usr/local/ssl/bin/fipsld FIPSLD_CC=gcc | ||||
| # ./configure && make). But keep in mind[!] that if certified code | ||||
| # resides in a shared library, then fipsld *may not* be used and | ||||
| # end-developer should not modify application configuration and build | ||||
| # procedures. This is because in-core fingerprint and associated | ||||
| # procedures are already embedded into and executed in shared library | ||||
| # context. | ||||
| case `basename "${TARGET}"` in | ||||
| libcrypto*|libfips*|*.dll)		;; | ||||
| *)	case "$*" in | ||||
| 	*libcrypto.a*|*-lcrypto*|*fipscanister.o*)	;; | ||||
| 	*)	exec ${CC} "$@"		;; | ||||
| 	esac | ||||
| esac | ||||
| 
 | ||||
| [ -n "${TARGET}" ] || { echo 'no -o specified'; exit 1; } | ||||
| 
 | ||||
| # Turn on debugging output? | ||||
| (   while [ "x$1" != "x" -a "x$1" != "x-DDEBUG_FINGERPRINT_PREMAIN" ]; do shift; done; | ||||
|     [ $# -ge 1 ] | ||||
| ) && set -x | ||||
| 
 | ||||
| THERE="`echo $0 | sed -e 's|[^/]*$||'`".. | ||||
| 
 | ||||
| # fipscanister.o can appear in command line | ||||
| CANISTER_O=`(while [ "x$1" != "x" ]; do case "$1" in *fipscanister.o) echo $1; exit;; esac; shift; done)` | ||||
| if [ -z "${CANISTER_O}" ]; then | ||||
| 	# If set, FIPSLIBDIR is location of installed validated FIPS module | ||||
| 	if [ -n "${FIPSLIBDIR}" ]; then | ||||
| 		CANISTER_O="${FIPSLIBDIR}/fipscanister.o" | ||||
| 	elif [ -f "${THERE}/fips/fipscanister.o" ]; then | ||||
| 		CANISTER_O="${THERE}/fips/fipscanister.o" | ||||
| 	elif [ -f "${THERE}/lib/fipscanister.o" ]; then | ||||
| 		CANISTER_O="${THERE}/lib/fipscanister.o" | ||||
| 	fi | ||||
| 	CANISTER_O_CMD="${CANISTER_O}" | ||||
| fi | ||||
| [ -f ${CANISTER_O} ] || { echo "unable to find ${CANISTER_O}"; exit 1; } | ||||
| 
 | ||||
| PREMAIN_C=`dirname "${CANISTER_O}"`/fips_premain.c | ||||
| 
 | ||||
| HMAC_KEY="etaonrishdlcupfm" | ||||
| 
 | ||||
| case "`(uname -s) 2>/dev/null`" in | ||||
| OSF1|IRIX*)	_WL_PREMAIN="-Wl,-init,FINGERPRINT_premain"	;; | ||||
| HP-UX)		_WL_PREMAIN="-Wl,+init,FINGERPRINT_premain"	;; | ||||
| AIX)		_WL_PREMAIN="-Wl,-binitfini:FINGERPRINT_premain,-bnoobjreorder";; | ||||
| Darwin)		(   while [ "x$1" != "x" -a "x$1" != "x-dynamiclib" ]; do shift; done; | ||||
| 		    [ $# -ge 1 ] | ||||
| 		) && _WL_PREMAIN="-Wl,-init,_FINGERPRINT_premain" ;; | ||||
| esac | ||||
| 
 | ||||
| case "${TARGET}" in | ||||
| [!/]*)	TARGET=./${TARGET} ;; | ||||
| esac | ||||
| 
 | ||||
| case `basename "${TARGET}"` in | ||||
| lib*|*.dll)	# must be linking a shared lib... | ||||
| 	# Shared lib creation can be taking place in the source | ||||
| 	# directory only, but fipscanister.o can reside elsewhere... | ||||
| 	FINGERTYPE="${THERE}/fips/fips_standalone_sha1" | ||||
| 
 | ||||
| 	# verify fipspremain.c against its detached signature... | ||||
| 	${FINGERTYPE} "${PREMAIN_C}" | sed "s/(.*\//(/" | \ | ||||
| 		diff -w "${PREMAIN_C}.sha1" - || \ | ||||
| 	{ echo "${PREMAIN_C} fingerprint mismatch"; exit 1; } | ||||
| 	# verify fipscanister.o against its detached signature... | ||||
| 	${FINGERTYPE} "${CANISTER_O}" | sed "s/(.*\//(/" | \ | ||||
| 		diff -w "${CANISTER_O}.sha1" - || \ | ||||
| 	{ echo "${CANISTER_O} fingerprint mismatch"; exit 1; } | ||||
| 
 | ||||
| 	# Temporarily remove fipscanister.o from libcrypto.a! | ||||
| 	# We are required to use the standalone copy... | ||||
| 	if [ -f "${THERE}/libcrypto.a" ]; then | ||||
| 	    if ar d "${THERE}/libcrypto.a" fipscanister.o; then | ||||
| 		(ranlib "${THERE}/libcrypto.a") 2>/dev/null || : | ||||
| 		trap	'ar r "${THERE}/libcrypto.a" "${CANISTER_O}"; | ||||
| 			 (ranlib "${THERE}/libcrypto.a") 2>/dev/null || :; | ||||
| 			 sleep 1; | ||||
| 			 touch -c "${TARGET}"' 0 | ||||
| 	    fi | ||||
| 	fi | ||||
| 
 | ||||
| 	/bin/rm -f "${TARGET}" | ||||
| 	${CC}	${CANISTER_O_CMD:+"${CANISTER_O_CMD}"} \ | ||||
| 		"${PREMAIN_C}" \ | ||||
| 		${_WL_PREMAIN} "$@" | ||||
| 
 | ||||
| 	# generate signature... | ||||
| 	if [ -z "${FIPS_SIG}" ]; then | ||||
| 		SIG=`"${THERE}/fips/fips_premain_dso" "${TARGET}"` | ||||
| 	else | ||||
| 		SIG=`"${FIPS_SIG}" -dso "${TARGET}"` | ||||
| 	fi | ||||
| 	/bin/rm -f "${TARGET}" | ||||
| 	if [ -z "${SIG}" ]; then | ||||
| 	   echo "unable to collect signature"; exit 1 | ||||
| 	fi | ||||
| 
 | ||||
| 	# recompile with signature... | ||||
| 	${CC}	${CANISTER_O_CMD:+"${CANISTER_O_CMD}"} \ | ||||
| 		-DHMAC_SHA1_SIG=\"${SIG}\" "${PREMAIN_C}" \ | ||||
| 		${_WL_PREMAIN} "$@" | ||||
| 	;; | ||||
| 
 | ||||
| *)	# must be linking statically... | ||||
| 	# Static linking can be taking place either in the source | ||||
| 	# directory or off the installed binary target destination. | ||||
| 	if [ -x "${THERE}/fips/fips_standalone_sha1" ]; then | ||||
| 		FINGERTYPE="${THERE}/fips/fips_standalone_sha1" | ||||
| 	else	# Installed tree is expected to contain | ||||
| 		# lib/fipscanister.o, lib/fipscanister.o.sha1 and | ||||
| 		# lib/fips_premain.c [not to mention bin/openssl]. | ||||
| 		FINGERTYPE="${THERE}/bin/openssl sha1 -hmac ${HMAC_KEY}" | ||||
| 	fi | ||||
| 
 | ||||
| 	# verify fipscanister.o against its detached signature... | ||||
| 	${FINGERTYPE} "${CANISTER_O}" | sed "s/(.*\//(/" | \ | ||||
| 		diff -w "${CANISTER_O}.sha1" - || \ | ||||
| 	{ echo "${CANISTER_O} fingerprint mismatch"; exit 1; } | ||||
| 
 | ||||
| 	# verify fips_premain.c against its detached signature... | ||||
| 	${FINGERTYPE} "${PREMAIN_C}" | sed "s/(.*\//(/" | \ | ||||
| 		diff -w "${PREMAIN_C}.sha1" - || \ | ||||
| 	{ echo "${PREMAIN_C} fingerprint mismatch"; exit 1; } | ||||
| 
 | ||||
| 	/bin/rm -f "${TARGET}" | ||||
| 	${CC}	${CANISTER_O_CMD:+"${CANISTER_O_CMD}"} \ | ||||
| 		"${PREMAIN_C}" \ | ||||
| 		${_WL_PREMAIN} "$@" | ||||
| 
 | ||||
| 	# generate signature... | ||||
| 	if [ -z "${FIPS_SIG}" ]; then | ||||
| 		SIG=`"${TARGET}"` | ||||
| 	else | ||||
| 		SIG=`"${FIPS_SIG}" -exe "${TARGET}"` | ||||
| 	fi | ||||
| 	/bin/rm -f "${TARGET}" | ||||
| 	if [ -z "${SIG}" ]; then | ||||
| 	   echo "unable to collect signature"; exit 1 | ||||
| 	fi | ||||
| 
 | ||||
| 	# recompile with signature... | ||||
| 	${CC}	${CANISTER_O_CMD:+"${CANISTER_O_CMD}"} \ | ||||
| 		-DHMAC_SHA1_SIG=\"${SIG}\" "${PREMAIN_C}" \ | ||||
| 		${_WL_PREMAIN} "$@" | ||||
| 	;; | ||||
| esac | ||||
|  | @ -0,0 +1,4 @@ | |||
| lib | ||||
| Makefile.save | ||||
| *.flc | ||||
| semantic.cache | ||||
|  | @ -0,0 +1,123 @@ | |||
| #
 | ||||
| # OpenSSL/fips/hmac/Makefile
 | ||||
| #
 | ||||
| 
 | ||||
| DIR=	hmac | ||||
| TOP=	../.. | ||||
| CC=	cc | ||||
| INCLUDES= | ||||
| CFLAG=-g | ||||
| INSTALL_PREFIX= | ||||
| OPENSSLDIR=     /usr/local/ssl | ||||
| INSTALLTOP=/usr/local/ssl | ||||
| MAKEDEPPROG=	makedepend | ||||
| MAKEDEPEND=	$(TOP)/util/domd $(TOP) -MD $(MAKEDEPPROG) | ||||
| MAKEFILE=	Makefile | ||||
| AR=		ar r | ||||
| 
 | ||||
| CFLAGS= $(INCLUDES) $(CFLAG) | ||||
| 
 | ||||
| GENERAL=Makefile | ||||
| TEST=fips_hmactest.c | ||||
| APPS= | ||||
| 
 | ||||
| LIB=$(TOP)/libcrypto.a | ||||
| LIBSRC= fips_hmac_selftest.c | ||||
| LIBOBJ= fips_hmac_selftest.o | ||||
| 
 | ||||
| SRC= $(LIBSRC) | ||||
| 
 | ||||
| EXHEADER= | ||||
| HEADER=	$(EXHEADER) | ||||
| 
 | ||||
| ALL=    $(GENERAL) $(SRC) $(HEADER) | ||||
| 
 | ||||
| top: | ||||
| 	(cd $(TOP); $(MAKE) DIRS=fips FDIRS=$(DIR) sub_all) | ||||
| 
 | ||||
| all:	lib | ||||
| 
 | ||||
| lib:	$(LIBOBJ) | ||||
| 	@echo $(LIBOBJ) > lib | ||||
| 
 | ||||
| files: | ||||
| 	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO | ||||
| 
 | ||||
| links: | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/include/openssl $(EXHEADER) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/test $(TEST) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/apps $(APPS) | ||||
| 
 | ||||
| install: | ||||
| 	@headerlist="$(EXHEADER)"; for i in $$headerlist; \
 | ||||
| 	do \
 | ||||
| 	  (cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
 | ||||
| 	  chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
 | ||||
| 	done | ||||
| 
 | ||||
| tags: | ||||
| 	ctags $(SRC) | ||||
| 
 | ||||
| tests: | ||||
| 
 | ||||
| Q=../testvectors/hmac/req | ||||
| A=../testvectors/hmac/rsp | ||||
| 
 | ||||
| fips_test: | ||||
| 	-rm -rf $(A) | ||||
| 	mkdir $(A) | ||||
| 	if [ -f $(Q)/HMAC.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_hmactest < $(Q)/HMAC.req > $(A)/HMAC.rsp; fi | ||||
| 
 | ||||
| lint: | ||||
| 	lint -DLINT $(INCLUDES) $(SRC)>fluff | ||||
| 
 | ||||
| depend: | ||||
| 	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(SRC) $(TEST) | ||||
| 
 | ||||
| dclean: | ||||
| 	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new | ||||
| 	mv -f Makefile.new $(MAKEFILE) | ||||
| 
 | ||||
| clean: | ||||
| 	rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff | ||||
| # DO NOT DELETE THIS LINE -- make depend depends on it.
 | ||||
| 
 | ||||
| fips_hmac.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_hmac.o: ../../include/openssl/crypto.h ../../include/openssl/e_os2.h | ||||
| fips_hmac.o: ../../include/openssl/evp.h ../../include/openssl/fips.h | ||||
| fips_hmac.o: ../../include/openssl/hmac.h ../../include/openssl/obj_mac.h | ||||
| fips_hmac.o: ../../include/openssl/objects.h | ||||
| fips_hmac.o: ../../include/openssl/opensslconf.h | ||||
| fips_hmac.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h | ||||
| fips_hmac.o: ../../include/openssl/safestack.h ../../include/openssl/stack.h | ||||
| fips_hmac.o: ../../include/openssl/symhacks.h fips_hmac.c | ||||
| fips_hmac_selftest.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/crypto.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/evp.h ../../include/openssl/fips.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/hmac.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/lhash.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/obj_mac.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/objects.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/opensslconf.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/opensslv.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/ossl_typ.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/safestack.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/stack.h | ||||
| fips_hmac_selftest.o: ../../include/openssl/symhacks.h fips_hmac_selftest.c | ||||
| fips_hmactest.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_hmactest.o: ../../include/openssl/bn.h ../../include/openssl/buffer.h | ||||
| fips_hmactest.o: ../../include/openssl/conf.h ../../include/openssl/crypto.h | ||||
| fips_hmactest.o: ../../include/openssl/e_os2.h ../../include/openssl/ec.h | ||||
| fips_hmactest.o: ../../include/openssl/ecdh.h ../../include/openssl/ecdsa.h | ||||
| fips_hmactest.o: ../../include/openssl/err.h ../../include/openssl/evp.h | ||||
| fips_hmactest.o: ../../include/openssl/fips.h ../../include/openssl/hmac.h | ||||
| fips_hmactest.o: ../../include/openssl/lhash.h ../../include/openssl/obj_mac.h | ||||
| fips_hmactest.o: ../../include/openssl/objects.h | ||||
| fips_hmactest.o: ../../include/openssl/opensslconf.h | ||||
| fips_hmactest.o: ../../include/openssl/opensslv.h | ||||
| fips_hmactest.o: ../../include/openssl/ossl_typ.h ../../include/openssl/pkcs7.h | ||||
| fips_hmactest.o: ../../include/openssl/safestack.h ../../include/openssl/sha.h | ||||
| fips_hmactest.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_hmactest.o: ../../include/openssl/x509.h ../../include/openssl/x509_vfy.h | ||||
| fips_hmactest.o: ../../include/openssl/x509v3.h ../fips_utl.h fips_hmactest.c | ||||
|  | @ -0,0 +1,135 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/hmac.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| typedef struct { | ||||
| 	const EVP_MD *(*alg)(void); | ||||
| 	const char *key, *iv; | ||||
| 	unsigned char kaval[EVP_MAX_MD_SIZE]; | ||||
| } HMAC_KAT; | ||||
| 
 | ||||
| static const HMAC_KAT vector[] = { | ||||
|     {	EVP_sha1, | ||||
| 	/* from http://csrc.nist.gov/publications/fips/fips198/fips-198a.pdf */ | ||||
| 	"0123456789:;<=>?@ABC", | ||||
| 	"Sample #2", | ||||
| 	{ 0x09,0x22,0xd3,0x40,0x5f,0xaa,0x3d,0x19, | ||||
| 	  0x4f,0x82,0xa4,0x58,0x30,0x73,0x7d,0x5c, | ||||
| 	  0xc6,0xc7,0x5d,0x24 } | ||||
|     }, | ||||
|     {	EVP_sha224, | ||||
| 	/* just keep extending the above... */ | ||||
| 	"0123456789:;<=>?@ABC", | ||||
| 	"Sample #2", | ||||
| 	{ 0xdd,0xef,0x0a,0x40,0xcb,0x7d,0x50,0xfb, | ||||
| 	  0x6e,0xe6,0xce,0xa1,0x20,0xba,0x26,0xaa, | ||||
| 	  0x08,0xf3,0x07,0x75,0x87,0xb8,0xad,0x1b, | ||||
| 	  0x8c,0x8d,0x12,0xc7 } | ||||
|     }, | ||||
|     {	EVP_sha256, | ||||
| 	"0123456789:;<=>?@ABC", | ||||
| 	"Sample #2", | ||||
| 	{ 0xb8,0xf2,0x0d,0xb5,0x41,0xea,0x43,0x09, | ||||
| 	  0xca,0x4e,0xa9,0x38,0x0c,0xd0,0xe8,0x34, | ||||
| 	  0xf7,0x1f,0xbe,0x91,0x74,0xa2,0x61,0x38, | ||||
| 	  0x0d,0xc1,0x7e,0xae,0x6a,0x34,0x51,0xd9 } | ||||
|     }, | ||||
|     {	EVP_sha384, | ||||
| 	"0123456789:;<=>?@ABC", | ||||
| 	"Sample #2", | ||||
| 	{ 0x08,0xbc,0xb0,0xda,0x49,0x1e,0x87,0xad, | ||||
| 	  0x9a,0x1d,0x6a,0xce,0x23,0xc5,0x0b,0xf6, | ||||
| 	  0xb7,0x18,0x06,0xa5,0x77,0xcd,0x49,0x04, | ||||
| 	  0x89,0xf1,0xe6,0x23,0x44,0x51,0x51,0x9f, | ||||
| 	  0x85,0x56,0x80,0x79,0x0c,0xbd,0x4d,0x50, | ||||
| 	  0xa4,0x5f,0x29,0xe3,0x93,0xf0,0xe8,0x7f } | ||||
|     }, | ||||
|     {	EVP_sha512, | ||||
| 	"0123456789:;<=>?@ABC", | ||||
| 	"Sample #2", | ||||
| 	{ 0x80,0x9d,0x44,0x05,0x7c,0x5b,0x95,0x41, | ||||
| 	  0x05,0xbd,0x04,0x13,0x16,0xdb,0x0f,0xac, | ||||
| 	  0x44,0xd5,0xa4,0xd5,0xd0,0x89,0x2b,0xd0, | ||||
| 	  0x4e,0x86,0x64,0x12,0xc0,0x90,0x77,0x68, | ||||
| 	  0xf1,0x87,0xb7,0x7c,0x4f,0xae,0x2c,0x2f, | ||||
| 	  0x21,0xa5,0xb5,0x65,0x9a,0x4f,0x4b,0xa7, | ||||
| 	  0x47,0x02,0xa3,0xde,0x9b,0x51,0xf1,0x45, | ||||
| 	  0xbd,0x4f,0x25,0x27,0x42,0x98,0x99,0x05 } | ||||
|     }, | ||||
| }; | ||||
| 
 | ||||
| int FIPS_selftest_hmac() | ||||
|     { | ||||
|     size_t n; | ||||
|     unsigned int    outlen; | ||||
|     unsigned char   out[EVP_MAX_MD_SIZE]; | ||||
|     const EVP_MD   *md; | ||||
|     const HMAC_KAT *t; | ||||
| 
 | ||||
|     for(n=0,t=vector; n<sizeof(vector)/sizeof(vector[0]); n++,t++) | ||||
| 	{ | ||||
| 	md = (*t->alg)(); | ||||
| 	HMAC(md,t->key,strlen(t->key), | ||||
| 		(const unsigned char *)t->iv,strlen(t->iv), | ||||
| 		out,&outlen); | ||||
| 
 | ||||
| 	if(memcmp(out,t->kaval,outlen)) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_FIPS_SELFTEST_HMAC,FIPS_R_SELFTEST_FAILED); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 	} | ||||
|     return 1; | ||||
|     } | ||||
| #endif | ||||
|  | @ -0,0 +1,322 @@ | |||
| /* fips_hmactest.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2005. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <ctype.h> | ||||
| #include <string.h> | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #include <openssl/x509v3.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS HMAC support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| static int hmac_test(const EVP_MD *md, FILE *out, FILE *in); | ||||
| static int print_hmac(const EVP_MD *md, FILE *out, | ||||
| 		unsigned char *Key, int Klen, | ||||
| 		unsigned char *Msg, int Msglen, int Tlen); | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| 	{ | ||||
| 	FILE *in = NULL, *out = NULL; | ||||
| 
 | ||||
| 	int ret = 1; | ||||
| 	fips_set_error_print(); | ||||
| 	if(!FIPS_mode_set(1)) | ||||
| 		goto end; | ||||
| 
 | ||||
| 	if (argc == 1) | ||||
| 		in = stdin; | ||||
| 	else | ||||
| 		in = fopen(argv[1], "r"); | ||||
| 
 | ||||
| 	if (argc < 2) | ||||
| 		out = stdout; | ||||
| 	else | ||||
| 		out = fopen(argv[2], "w"); | ||||
| 
 | ||||
| 	if (!in) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL input initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!out) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL output initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!hmac_test(EVP_sha1(), out, in)) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL hmac file processing error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 	else | ||||
| 		ret = 0; | ||||
| 
 | ||||
| 	end: | ||||
| 
 | ||||
| 	if (in && (in != stdin)) | ||||
| 		fclose(in); | ||||
| 	if (out && (out != stdout)) | ||||
| 		fclose(out); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| #define HMAC_TEST_MAXLINELEN	1024 | ||||
| 
 | ||||
| int hmac_test(const EVP_MD *md, FILE *out, FILE *in) | ||||
| 	{ | ||||
| 	char *linebuf, *olinebuf, *p, *q; | ||||
| 	char *keyword, *value; | ||||
| 	unsigned char *Key = NULL, *Msg = NULL; | ||||
| 	int Count, Klen, Tlen; | ||||
| 	long Keylen, Msglen; | ||||
| 	int ret = 0; | ||||
| 	int lnum = 0; | ||||
| 
 | ||||
| 	olinebuf = OPENSSL_malloc(HMAC_TEST_MAXLINELEN); | ||||
| 	linebuf = OPENSSL_malloc(HMAC_TEST_MAXLINELEN); | ||||
| 
 | ||||
| 	if (!linebuf || !olinebuf) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	Count = -1; | ||||
| 	Klen = -1; | ||||
| 	Tlen = -1; | ||||
| 
 | ||||
| 	while (fgets(olinebuf, HMAC_TEST_MAXLINELEN, in)) | ||||
| 		{ | ||||
| 		lnum++; | ||||
| 		strcpy(linebuf, olinebuf); | ||||
| 		keyword = linebuf; | ||||
| 		/* Skip leading space */ | ||||
| 		while (isspace((unsigned char)*keyword)) | ||||
| 			keyword++; | ||||
| 
 | ||||
| 		/* Look for = sign */ | ||||
| 		p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 		/* If no = or starts with [ (for [L=20] line) just copy */ | ||||
| 		if (!p) | ||||
| 			{ | ||||
| 			if (fputs(olinebuf, out) < 0) | ||||
| 				goto error; | ||||
| 			continue; | ||||
| 			} | ||||
| 
 | ||||
| 		q = p - 1; | ||||
| 
 | ||||
| 		/* Remove trailing space */ | ||||
| 		while (isspace((unsigned char)*q)) | ||||
| 			*q-- = 0; | ||||
| 
 | ||||
| 		*p = 0; | ||||
| 		value = p + 1; | ||||
| 
 | ||||
| 		/* Remove leading space from value */ | ||||
| 		while (isspace((unsigned char)*value)) | ||||
| 			value++; | ||||
| 
 | ||||
| 		/* Remove trailing space from value */ | ||||
| 		p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 		while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 			*p-- = 0; | ||||
| 
 | ||||
| 		if (!strcmp(keyword,"[L") && *p==']') | ||||
| 			{ | ||||
| 			switch (atoi(value)) | ||||
| 				{ | ||||
| 				case 20: md=EVP_sha1();   break; | ||||
| 				case 28: md=EVP_sha224(); break; | ||||
| 				case 32: md=EVP_sha256(); break; | ||||
| 				case 48: md=EVP_sha384(); break; | ||||
| 				case 64: md=EVP_sha512(); break; | ||||
| 				default: goto parse_error; | ||||
| 				} | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Count")) | ||||
| 			{ | ||||
| 			if (Count != -1) | ||||
| 				goto parse_error; | ||||
| 			Count = atoi(value); | ||||
| 			if (Count < 0) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Klen")) | ||||
| 			{ | ||||
| 			if (Klen != -1) | ||||
| 				goto parse_error; | ||||
| 			Klen = atoi(value); | ||||
| 			if (Klen < 0) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Tlen")) | ||||
| 			{ | ||||
| 			if (Tlen != -1) | ||||
| 				goto parse_error; | ||||
| 			Tlen = atoi(value); | ||||
| 			if (Tlen < 0) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Msg")) | ||||
| 			{ | ||||
| 			if (Msg) | ||||
| 				goto parse_error; | ||||
| 			Msg = hex2bin_m(value, &Msglen); | ||||
| 			if (!Msg) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Key")) | ||||
| 			{ | ||||
| 			if (Key) | ||||
| 				goto parse_error; | ||||
| 			Key = hex2bin_m(value, &Keylen); | ||||
| 			if (!Key) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Mac")) | ||||
| 			continue; | ||||
| 		else | ||||
| 			goto parse_error; | ||||
| 
 | ||||
| 		fputs(olinebuf, out); | ||||
| 
 | ||||
| 		if (Key && Msg && (Tlen > 0) && (Klen > 0)) | ||||
| 			{ | ||||
| 			if (!print_hmac(md, out, Key, Klen, Msg, Msglen, Tlen)) | ||||
| 				goto error; | ||||
| 			OPENSSL_free(Key); | ||||
| 			Key = NULL; | ||||
| 			OPENSSL_free(Msg); | ||||
| 			Msg = NULL; | ||||
| 			Klen = -1; | ||||
| 			Tlen = -1; | ||||
| 			Count = -1; | ||||
| 			} | ||||
| 
 | ||||
| 		} | ||||
| 
 | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 
 | ||||
| 	error: | ||||
| 
 | ||||
| 	if (olinebuf) | ||||
| 		OPENSSL_free(olinebuf); | ||||
| 	if (linebuf) | ||||
| 		OPENSSL_free(linebuf); | ||||
| 	if (Key) | ||||
| 		OPENSSL_free(Key); | ||||
| 	if (Msg) | ||||
| 		OPENSSL_free(Msg); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	parse_error: | ||||
| 
 | ||||
| 	fprintf(stderr, "FATAL parse error processing line %d\n", lnum); | ||||
| 
 | ||||
| 	goto error; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| static int print_hmac(const EVP_MD *emd, FILE *out, | ||||
| 		unsigned char *Key, int Klen, | ||||
| 		unsigned char *Msg, int Msglen, int Tlen) | ||||
| 	{ | ||||
| 	int i, mdlen; | ||||
| 	unsigned char md[EVP_MAX_MD_SIZE]; | ||||
| 	if (!HMAC(emd, Key, Klen, Msg, Msglen, md, | ||||
| 						(unsigned int *)&mdlen)) | ||||
| 		{ | ||||
| 		fputs("Error calculating HMAC\n", stderr); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	if (Tlen > mdlen) | ||||
| 		{ | ||||
| 		fputs("Parameter error, Tlen > HMAC length\n", stderr); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	fputs("Mac = ", out); | ||||
| 	for (i = 0; i < Tlen; i++) | ||||
| 		fprintf(out, "%02x", md[i]); | ||||
| 	fputs("\n", out); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,657 @@ | |||
| #!/usr/local/bin/perl -w | ||||
| # Quick & dirty utility to generate a script for executing the | ||||
| # FIPS 140-2 CMVP algorithm tests based on the pathnames of | ||||
| # input algorithm test files actually present (the unqualified | ||||
| # file names are consistent but the pathnames are not). | ||||
| # | ||||
| 
 | ||||
| # List of all the unqualified file names we expect. | ||||
| my %fips_tests = ( | ||||
| 
 | ||||
| # FIPS test definitions | ||||
| 
 | ||||
| # DSA tests | ||||
| 
 | ||||
| "PQGGen" => "fips_dssvs pqg", | ||||
| "KeyPair" => "fips_dssvs keypair", | ||||
| "SigGen" => "fips_dssvs siggen", | ||||
| "SigVer" => "fips_dssvs sigver", | ||||
| 
 | ||||
| # SHA tests | ||||
| 
 | ||||
| "SHA1LongMsg" => "fips_shatest", | ||||
| "SHA1Monte" => "fips_shatest", | ||||
| "SHA1ShortMsg" => "fips_shatest", | ||||
| "SHA224LongMsg" => "fips_shatest", | ||||
| "SHA224Monte" => "fips_shatest", | ||||
| "SHA224ShortMsg" => "fips_shatest", | ||||
| "SHA256LongMsg" => "fips_shatest", | ||||
| "SHA256Monte" => "fips_shatest", | ||||
| "SHA256ShortMsg" => "fips_shatest", | ||||
| "SHA384LongMsg" => "fips_shatest", | ||||
| "SHA384Monte" => "fips_shatest", | ||||
| "SHA384ShortMsg" => "fips_shatest", | ||||
| "SHA512LongMsg" => "fips_shatest", | ||||
| "SHA512Monte" => "fips_shatest", | ||||
| "SHA512ShortMsg" => "fips_shatest", | ||||
| 
 | ||||
| # HMAC | ||||
| 
 | ||||
| "HMAC" => "fips_hmactest", | ||||
| 
 | ||||
| # RAND tests | ||||
| 
 | ||||
| "ANSI931_AES128MCT" => "fips_rngvs mct", | ||||
| "ANSI931_AES192MCT" => "fips_rngvs mct", | ||||
| "ANSI931_AES256MCT" => "fips_rngvs mct", | ||||
| "ANSI931_AES128VST" => "fips_rngvs vst", | ||||
| "ANSI931_AES192VST" => "fips_rngvs vst", | ||||
| "ANSI931_AES256VST" => "fips_rngvs vst", | ||||
| 
 | ||||
| # RSA tests | ||||
| 
 | ||||
| "SigGen15" => "fips_rsastest", | ||||
| "SigVer15" => "fips_rsavtest", | ||||
| "SigGenPSS" => "fips_rsastest -saltlen SALT", | ||||
| "SigVerPSS" => "fips_rsavtest -saltlen SALT", | ||||
| "SigGenRSA" => "fips_rsastest -x931", | ||||
| "SigVerRSA" => "fips_rsavtest -x931", | ||||
| "KeyGenRSA" => "fips_rsagtest", | ||||
| 
 | ||||
| # AES tests | ||||
| 
 | ||||
| "CBCGFSbox128" => "fips_aesavs -f", | ||||
| "CBCGFSbox192" => "fips_aesavs -f", | ||||
| "CBCGFSbox256" => "fips_aesavs -f", | ||||
| "CBCKeySbox128" => "fips_aesavs -f", | ||||
| "CBCKeySbox192" => "fips_aesavs -f", | ||||
| "CBCKeySbox256" => "fips_aesavs -f", | ||||
| "CBCMCT128" => "fips_aesavs -f", | ||||
| "CBCMCT192" => "fips_aesavs -f", | ||||
| "CBCMCT256" => "fips_aesavs -f", | ||||
| "CBCMMT128" => "fips_aesavs -f", | ||||
| "CBCMMT192" => "fips_aesavs -f", | ||||
| "CBCMMT256" => "fips_aesavs -f", | ||||
| "CBCVarKey128" => "fips_aesavs -f", | ||||
| "CBCVarKey192" => "fips_aesavs -f", | ||||
| "CBCVarKey256" => "fips_aesavs -f", | ||||
| "CBCVarTxt128" => "fips_aesavs -f", | ||||
| "CBCVarTxt192" => "fips_aesavs -f", | ||||
| "CBCVarTxt256" => "fips_aesavs -f", | ||||
| "CFB128GFSbox128" => "fips_aesavs -f", | ||||
| "CFB128GFSbox192" => "fips_aesavs -f", | ||||
| "CFB128GFSbox256" => "fips_aesavs -f", | ||||
| "CFB128KeySbox128" => "fips_aesavs -f", | ||||
| "CFB128KeySbox192" => "fips_aesavs -f", | ||||
| "CFB128KeySbox256" => "fips_aesavs -f", | ||||
| "CFB128MCT128" => "fips_aesavs -f", | ||||
| "CFB128MCT192" => "fips_aesavs -f", | ||||
| "CFB128MCT256" => "fips_aesavs -f", | ||||
| "CFB128MMT128" => "fips_aesavs -f", | ||||
| "CFB128MMT192" => "fips_aesavs -f", | ||||
| "CFB128MMT256" => "fips_aesavs -f", | ||||
| "CFB128VarKey128" => "fips_aesavs -f", | ||||
| "CFB128VarKey192" => "fips_aesavs -f", | ||||
| "CFB128VarKey256" => "fips_aesavs -f", | ||||
| "CFB128VarTxt128" => "fips_aesavs -f", | ||||
| "CFB128VarTxt192" => "fips_aesavs -f", | ||||
| "CFB128VarTxt256" => "fips_aesavs -f", | ||||
| "CFB8GFSbox128" => "fips_aesavs -f", | ||||
| "CFB8GFSbox192" => "fips_aesavs -f", | ||||
| "CFB8GFSbox256" => "fips_aesavs -f", | ||||
| "CFB8KeySbox128" => "fips_aesavs -f", | ||||
| "CFB8KeySbox192" => "fips_aesavs -f", | ||||
| "CFB8KeySbox256" => "fips_aesavs -f", | ||||
| "CFB8MCT128" => "fips_aesavs -f", | ||||
| "CFB8MCT192" => "fips_aesavs -f", | ||||
| "CFB8MCT256" => "fips_aesavs -f", | ||||
| "CFB8MMT128" => "fips_aesavs -f", | ||||
| "CFB8MMT192" => "fips_aesavs -f", | ||||
| "CFB8MMT256" => "fips_aesavs -f", | ||||
| "CFB8VarKey128" => "fips_aesavs -f", | ||||
| "CFB8VarKey192" => "fips_aesavs -f", | ||||
| "CFB8VarKey256" => "fips_aesavs -f", | ||||
| "CFB8VarTxt128" => "fips_aesavs -f", | ||||
| "CFB8VarTxt192" => "fips_aesavs -f", | ||||
| "CFB8VarTxt256" => "fips_aesavs -f", | ||||
| #"CFB1GFSbox128" => "fips_aesavs -f", | ||||
| #"CFB1GFSbox192" => "fips_aesavs -f", | ||||
| #"CFB1GFSbox256" => "fips_aesavs -f", | ||||
| #"CFB1KeySbox128" => "fips_aesavs -f", | ||||
| #"CFB1KeySbox192" => "fips_aesavs -f", | ||||
| #"CFB1KeySbox256" => "fips_aesavs -f", | ||||
| #"CFB1MCT128" => "fips_aesavs -f", | ||||
| #"CFB1MCT192" => "fips_aesavs -f", | ||||
| #"CFB1MCT256" => "fips_aesavs -f", | ||||
| #"CFB1MMT128" => "fips_aesavs -f", | ||||
| #"CFB1MMT192" => "fips_aesavs -f", | ||||
| #"CFB1MMT256" => "fips_aesavs -f", | ||||
| #"CFB1VarKey128" => "fips_aesavs -f", | ||||
| #"CFB1VarKey192" => "fips_aesavs -f", | ||||
| #"CFB1VarKey256" => "fips_aesavs -f", | ||||
| #"CFB1VarTxt128" => "fips_aesavs -f", | ||||
| #"CFB1VarTxt192" => "fips_aesavs -f", | ||||
| #"CFB1VarTxt256" => "fips_aesavs -f", | ||||
| "ECBGFSbox128" => "fips_aesavs -f", | ||||
| "ECBGFSbox192" => "fips_aesavs -f", | ||||
| "ECBGFSbox256" => "fips_aesavs -f", | ||||
| "ECBKeySbox128" => "fips_aesavs -f", | ||||
| "ECBKeySbox192" => "fips_aesavs -f", | ||||
| "ECBKeySbox256" => "fips_aesavs -f", | ||||
| "ECBMCT128" => "fips_aesavs -f", | ||||
| "ECBMCT192" => "fips_aesavs -f", | ||||
| "ECBMCT256" => "fips_aesavs -f", | ||||
| "ECBMMT128" => "fips_aesavs -f", | ||||
| "ECBMMT192" => "fips_aesavs -f", | ||||
| "ECBMMT256" => "fips_aesavs -f", | ||||
| "ECBVarKey128" => "fips_aesavs -f", | ||||
| "ECBVarKey192" => "fips_aesavs -f", | ||||
| "ECBVarKey256" => "fips_aesavs -f", | ||||
| "ECBVarTxt128" => "fips_aesavs -f", | ||||
| "ECBVarTxt192" => "fips_aesavs -f", | ||||
| "ECBVarTxt256" => "fips_aesavs -f", | ||||
| "OFBGFSbox128" => "fips_aesavs -f", | ||||
| "OFBGFSbox192" => "fips_aesavs -f", | ||||
| "OFBGFSbox256" => "fips_aesavs -f", | ||||
| "OFBKeySbox128" => "fips_aesavs -f", | ||||
| "OFBKeySbox192" => "fips_aesavs -f", | ||||
| "OFBKeySbox256" => "fips_aesavs -f", | ||||
| "OFBMCT128" => "fips_aesavs -f", | ||||
| "OFBMCT192" => "fips_aesavs -f", | ||||
| "OFBMCT256" => "fips_aesavs -f", | ||||
| "OFBMMT128" => "fips_aesavs -f", | ||||
| "OFBMMT192" => "fips_aesavs -f", | ||||
| "OFBMMT256" => "fips_aesavs -f", | ||||
| "OFBVarKey128" => "fips_aesavs -f", | ||||
| "OFBVarKey192" => "fips_aesavs -f", | ||||
| "OFBVarKey256" => "fips_aesavs -f", | ||||
| "OFBVarTxt128" => "fips_aesavs -f", | ||||
| "OFBVarTxt192" => "fips_aesavs -f", | ||||
| "OFBVarTxt256" => "fips_aesavs -f", | ||||
| 
 | ||||
| # Triple DES tests | ||||
| 
 | ||||
| "TCBCinvperm" => "fips_desmovs -f", | ||||
| "TCBCMMT1" => "fips_desmovs -f", | ||||
| "TCBCMMT2" => "fips_desmovs -f", | ||||
| "TCBCMMT3" => "fips_desmovs -f", | ||||
| "TCBCMonte1" => "fips_desmovs -f", | ||||
| "TCBCMonte2" => "fips_desmovs -f", | ||||
| "TCBCMonte3" => "fips_desmovs -f", | ||||
| "TCBCpermop" => "fips_desmovs -f", | ||||
| "TCBCsubtab" => "fips_desmovs -f", | ||||
| "TCBCvarkey" => "fips_desmovs -f", | ||||
| "TCBCvartext" => "fips_desmovs -f", | ||||
| "TCFB64invperm" => "fips_desmovs -f", | ||||
| "TCFB64MMT1" => "fips_desmovs -f", | ||||
| "TCFB64MMT2" => "fips_desmovs -f", | ||||
| "TCFB64MMT3" => "fips_desmovs -f", | ||||
| "TCFB64Monte1" => "fips_desmovs -f", | ||||
| "TCFB64Monte2" => "fips_desmovs -f", | ||||
| "TCFB64Monte3" => "fips_desmovs -f", | ||||
| "TCFB64permop" => "fips_desmovs -f", | ||||
| "TCFB64subtab" => "fips_desmovs -f", | ||||
| "TCFB64varkey" => "fips_desmovs -f", | ||||
| "TCFB64vartext" => "fips_desmovs -f", | ||||
| "TCFB8invperm" => "fips_desmovs -f", | ||||
| "TCFB8MMT1" => "fips_desmovs -f", | ||||
| "TCFB8MMT2" => "fips_desmovs -f", | ||||
| "TCFB8MMT3" => "fips_desmovs -f", | ||||
| "TCFB8Monte1" => "fips_desmovs -f", | ||||
| "TCFB8Monte2" => "fips_desmovs -f", | ||||
| "TCFB8Monte3" => "fips_desmovs -f", | ||||
| "TCFB8permop" => "fips_desmovs -f", | ||||
| "TCFB8subtab" => "fips_desmovs -f", | ||||
| "TCFB8varkey" => "fips_desmovs -f", | ||||
| "TCFB8vartext" => "fips_desmovs -f", | ||||
| "TECBinvperm" => "fips_desmovs -f", | ||||
| "TECBMMT1" => "fips_desmovs -f", | ||||
| "TECBMMT2" => "fips_desmovs -f", | ||||
| "TECBMMT3" => "fips_desmovs -f", | ||||
| "TECBMonte1" => "fips_desmovs -f", | ||||
| "TECBMonte2" => "fips_desmovs -f", | ||||
| "TECBMonte3" => "fips_desmovs -f", | ||||
| "TECBpermop" => "fips_desmovs -f", | ||||
| "TECBsubtab" => "fips_desmovs -f", | ||||
| "TECBvarkey" => "fips_desmovs -f", | ||||
| "TECBvartext" => "fips_desmovs -f", | ||||
| "TOFBinvperm" => "fips_desmovs -f", | ||||
| "TOFBMMT1" => "fips_desmovs -f", | ||||
| "TOFBMMT2" => "fips_desmovs -f", | ||||
| "TOFBMMT3" => "fips_desmovs -f", | ||||
| "TOFBMonte1" => "fips_desmovs -f", | ||||
| "TOFBMonte2" => "fips_desmovs -f", | ||||
| "TOFBMonte3" => "fips_desmovs -f", | ||||
| "TOFBpermop" => "fips_desmovs -f", | ||||
| "TOFBsubtab" => "fips_desmovs -f", | ||||
| "TOFBvarkey" => "fips_desmovs -f", | ||||
| "TOFBvartext" => "fips_desmovs -f", | ||||
| "TCBCinvperm" => "fips_desmovs -f", | ||||
| "TCBCMMT1" => "fips_desmovs -f", | ||||
| "TCBCMMT2" => "fips_desmovs -f", | ||||
| "TCBCMMT3" => "fips_desmovs -f", | ||||
| "TCBCMonte1" => "fips_desmovs -f", | ||||
| "TCBCMonte2" => "fips_desmovs -f", | ||||
| "TCBCMonte3" => "fips_desmovs -f", | ||||
| "TCBCpermop" => "fips_desmovs -f", | ||||
| "TCBCsubtab" => "fips_desmovs -f", | ||||
| "TCBCvarkey" => "fips_desmovs -f", | ||||
| "TCBCvartext" => "fips_desmovs -f", | ||||
| "TCFB64invperm" => "fips_desmovs -f", | ||||
| "TCFB64MMT1" => "fips_desmovs -f", | ||||
| "TCFB64MMT2" => "fips_desmovs -f", | ||||
| "TCFB64MMT3" => "fips_desmovs -f", | ||||
| "TCFB64Monte1" => "fips_desmovs -f", | ||||
| "TCFB64Monte2" => "fips_desmovs -f", | ||||
| "TCFB64Monte3" => "fips_desmovs -f", | ||||
| "TCFB64permop" => "fips_desmovs -f", | ||||
| "TCFB64subtab" => "fips_desmovs -f", | ||||
| "TCFB64varkey" => "fips_desmovs -f", | ||||
| "TCFB64vartext" => "fips_desmovs -f", | ||||
| "TCFB8invperm" => "fips_desmovs -f", | ||||
| "TCFB8MMT1" => "fips_desmovs -f", | ||||
| "TCFB8MMT2" => "fips_desmovs -f", | ||||
| "TCFB8MMT3" => "fips_desmovs -f", | ||||
| "TCFB8Monte1" => "fips_desmovs -f", | ||||
| "TCFB8Monte2" => "fips_desmovs -f", | ||||
| "TCFB8Monte3" => "fips_desmovs -f", | ||||
| "TCFB8permop" => "fips_desmovs -f", | ||||
| "TCFB8subtab" => "fips_desmovs -f", | ||||
| "TCFB8varkey" => "fips_desmovs -f", | ||||
| "TCFB8vartext" => "fips_desmovs -f", | ||||
| "TECBinvperm" => "fips_desmovs -f", | ||||
| "TECBMMT1" => "fips_desmovs -f", | ||||
| "TECBMMT2" => "fips_desmovs -f", | ||||
| "TECBMMT3" => "fips_desmovs -f", | ||||
| "TECBMonte1" => "fips_desmovs -f", | ||||
| "TECBMonte2" => "fips_desmovs -f", | ||||
| "TECBMonte3" => "fips_desmovs -f", | ||||
| "TECBpermop" => "fips_desmovs -f", | ||||
| "TECBsubtab" => "fips_desmovs -f", | ||||
| "TECBvarkey" => "fips_desmovs -f", | ||||
| "TECBvartext" => "fips_desmovs -f", | ||||
| "TOFBinvperm" => "fips_desmovs -f", | ||||
| "TOFBMMT1" => "fips_desmovs -f", | ||||
| "TOFBMMT2" => "fips_desmovs -f", | ||||
| "TOFBMMT3" => "fips_desmovs -f", | ||||
| "TOFBMonte1" => "fips_desmovs -f", | ||||
| "TOFBMonte2" => "fips_desmovs -f", | ||||
| "TOFBMonte3" => "fips_desmovs -f", | ||||
| "TOFBpermop" => "fips_desmovs -f", | ||||
| "TOFBsubtab" => "fips_desmovs -f", | ||||
| "TOFBvarkey" => "fips_desmovs -f", | ||||
| "TOFBvartext" => "fips_desmovs -f" | ||||
| 
 | ||||
| ); | ||||
| my %salt_names = ( | ||||
| "SigVerPSS (salt 0)" => "SigVerPSS", | ||||
| "SigVerPSS (salt 62)" => "SigVerPSS", | ||||
| "SigGenPSS (salt 0)" => "SigGenPSS", | ||||
| "SigGenPSS (salt 62)" => "SigGenPSS", | ||||
| ); | ||||
| 
 | ||||
| 
 | ||||
| my $win32 = $^O =~ m/mswin/i; | ||||
| my $onedir = 0; | ||||
| my $filter = ""; | ||||
| my $tvdir; | ||||
| my $tprefix; | ||||
| my $shwrap_prefix; | ||||
| my $shwrap; | ||||
| my $rmcmd = "rm -rf"; | ||||
| my $mkcmd = "mkdir"; | ||||
| my $debug = 0; | ||||
| my $quiet = 0; | ||||
| my $rspdir = "rsp"; | ||||
| my $rspignore = 0; | ||||
| my @bogus = ();			# list of unmatched *.rsp files | ||||
| my $bufout = ''; | ||||
| my $bufdir = ''; | ||||
| my %_programs = ();		# list of external programs to check | ||||
| 
 | ||||
| foreach (@ARGV) | ||||
| 	{ | ||||
| 	if ($_ eq "--win32") | ||||
| 		{ | ||||
| 		$win32 = 1; | ||||
| 		} | ||||
| 	elsif ($_ eq "--onedir") | ||||
| 		{ | ||||
| 		$onedir = 1; | ||||
| 		} | ||||
| 	elsif ($_ eq "--debug") | ||||
| 		{ | ||||
| 		$debug = 1; | ||||
| 		} | ||||
| 	elsif ($_ eq "--quiet") | ||||
| 		{ | ||||
| 		$quiet = 1; | ||||
| 		} | ||||
| 	elsif (/--dir=(.*)$/) | ||||
| 		{ | ||||
| 		$tvdir = $1; | ||||
| 		} | ||||
| 	elsif (/--rspdir=(.*)$/) | ||||
| 		{ | ||||
| 		$rspdir = $1; | ||||
| 		} | ||||
| 	elsif (/--noshwrap$/) | ||||
| 		{ | ||||
| 		$shwrap = ""; | ||||
| 		} | ||||
| 	elsif (/--rspignore$/) | ||||
| 		{ | ||||
| 		$rspignore = 1; | ||||
| 		} | ||||
| 	elsif (/--tprefix=(.*)$/) | ||||
| 		{ | ||||
| 		$tprefix = $1; | ||||
| 		} | ||||
| 	elsif (/--shwrap_prefix=(.*)$/) | ||||
| 		{ | ||||
| 		$shwrap_prefix = $1; | ||||
| 		} | ||||
| 	elsif (/--filter=(.*)$/) | ||||
| 		{ | ||||
| 		$filter = $1; | ||||
| 		} | ||||
| 	elsif (/--mkdir=(.*)$/) | ||||
| 		{ | ||||
| 		$mkcmd = $1; | ||||
| 		} | ||||
| 	elsif (/--rm=(.*)$/) | ||||
| 		{ | ||||
| 		$rmcmd = $1; | ||||
| 		} | ||||
| 	elsif (/--outfile=(.*)$/) | ||||
| 		{ | ||||
| 		$outfile = $1; | ||||
| 		} | ||||
| 	else | ||||
| 		{ | ||||
| 		&Help(); | ||||
| 		exit(1); | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| $tvdir = "." unless defined $tvdir; | ||||
| 
 | ||||
| if ($win32) | ||||
| 	{ | ||||
| 	if (!defined $tprefix) | ||||
| 		{ | ||||
| 		if ($onedir) | ||||
| 			{ | ||||
| 			$tprefix = ".\\"; | ||||
| 			} | ||||
| 		else | ||||
| 			{ | ||||
| 			$tprefix = "..\\out32dll\\"; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 	$bufinit .= <<END; | ||||
| \@echo off | ||||
| rem Test vector run script | ||||
| rem Auto generated by mkfipsscr.pl script | ||||
| rem Do not edit | ||||
| 
 | ||||
| END | ||||
| 
 | ||||
| 	} | ||||
| else | ||||
| 	{ | ||||
| 	if ($onedir) | ||||
| 		{ | ||||
| 		$tprefix = "./" unless defined $tprefix; | ||||
| 		$shwrap_prefix = "./" unless defined $shwrap_prefix; | ||||
| 		} | ||||
| 	else | ||||
| 		{ | ||||
| 		$tprefix = "../test/" unless defined $tprefix; | ||||
| 		$shwrap_prefix = "../util/" unless defined $shwrap_prefix; | ||||
| 		} | ||||
| 
 | ||||
| 	$shwrap = "${shwrap_prefix}shlib_wrap.sh " unless defined $shwrap; | ||||
| 
 | ||||
| 	$bufinit .= <<END; | ||||
| #!/bin/sh | ||||
| 
 | ||||
| # Test vector run script | ||||
| # Auto generated by mkfipsscr.pl script | ||||
| # Do not edit | ||||
| 
 | ||||
| RM="$rmcmd" | ||||
| MKDIR="$mkcmd" | ||||
| TPREFIX=$tprefix | ||||
| END | ||||
| 
 | ||||
| 	} | ||||
| my %fips_found; | ||||
| foreach (keys %fips_tests) | ||||
| 	{ | ||||
| 	$fips_found{$_} = 0; | ||||
| 	} | ||||
| my %saltPSS; | ||||
| for (keys %salt_names) | ||||
| 	{ | ||||
| 	$salt_found{$_} = 0; | ||||
| 	} | ||||
| 
 | ||||
| recurse_test($win32, $tprefix, $filter, $tvdir); | ||||
| 
 | ||||
| while (($key, $value) = each %salt_found) | ||||
| 	{ | ||||
| 	&countentry($key, $value); | ||||
| 	delete $fips_found{$salt_names{$key}}; | ||||
| 	} | ||||
| while (($key, $value) = each %fips_found) | ||||
| 	{ | ||||
| 	&countentry($key, $value); | ||||
| 	} | ||||
| 
 | ||||
| # If no fatal errors write out the script file | ||||
| 	$outfile = "fipstests.sh" unless defined $outfile; | ||||
| 	open(OUT, ">$outfile") || die "Error opening $outfile: $!"; | ||||
| 	print OUT $bufinit; | ||||
| 	if (!$rspignore && @bogus) | ||||
| 		{ | ||||
| 		print STDERR "ERROR: please remove bogus *.rsp files\n"; | ||||
| 		print OUT <<EOF; | ||||
| echo $outfile generation failed due to presence of bogus *.rsp files | ||||
| EOF | ||||
| 		} | ||||
| 	else | ||||
| 		{ | ||||
| 		print OUT $bufout; | ||||
| 		} | ||||
| 	close OUT; | ||||
| 
 | ||||
| # Check for external programs | ||||
| 	for (keys %_programs) | ||||
| 		{ | ||||
| 		s/ .*$//; | ||||
| 		-x $_ || print STDERR "WARNING: program $_ not found\n"; | ||||
| 		} | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub Help { | ||||
| (my $cmd) = ($0 =~ m#([^/]+)$#); | ||||
| 	print <<EOF; | ||||
| $cmd: generate script for CMVP algorithm tests | ||||
| 	--debug                     Enable debug output | ||||
| 	--dir=<dirname>             Optional root for *.req file search | ||||
| 	--filter=<regexp> | ||||
| 	--onedir <dirname>          Assume all components in current directory | ||||
| 	--outfile=<filename>        Optional name of output script, default fipstests.{sh|bat} | ||||
| 	--rspdir=<dirname>          Name of subdirectories containing *.rsp files, default "resp" | ||||
| 	--rspignore                 Ignore any bogus *.rsp files | ||||
| 	--shwrap_prefix=<prefix> | ||||
| 	--tprefix=<prefix> | ||||
| 	--quiet                     Shhh.... | ||||
| 	--win32                     Generate script for Win32 environment | ||||
| EOF | ||||
| } | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub countentry { | ||||
| 	my ($key,$value) = @_; | ||||
| 	if ($value == 0) | ||||
| 		{ | ||||
| 		print STDERR "WARNING: test file $key not found\n" unless $quiet; | ||||
| 		} | ||||
| 	elsif ($value > 1) | ||||
| 		{ | ||||
| 		print STDERR "WARNING: test file $key found $value times\n" unless $quiet; | ||||
| 		} | ||||
| 	else  | ||||
| 		{ | ||||
| 		print STDERR "Found test file $key\n" if $debug; | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub recurse_test | ||||
| 	{ | ||||
| 	my ($win32, $tprefix, $filter, $dir) = @_; | ||||
| 	my $dirh; | ||||
| 	opendir($dirh, $dir); | ||||
| 	while ($_ = readdir($dirh)) | ||||
| 		{ | ||||
| 		next if ($_ eq "." || $_ eq ".."); | ||||
| 		$_ = "$dir/$_"; | ||||
| 		if (-f "$_") | ||||
| 			{ | ||||
| 			if (/\/([^\/]*)\.rsp$/) | ||||
| 				{ | ||||
| 				if (exists $fips_tests{$1}) | ||||
| 					{ | ||||
| 					$debug && print "DEBUG: $1 found, will be overwritten\n"; | ||||
| 					} | ||||
| 				else | ||||
| 					{ | ||||
| 					print STDERR "ERROR: bogus file $_\n"; | ||||
| 					push @bogus, $_; | ||||
| 					} | ||||
| 				} | ||||
| 			next unless /$filter.*\.req$/i; | ||||
| 			if (/\/([^\/]*)\.req$/ && exists $fips_tests{$1}) | ||||
| 				{ | ||||
| 				$fips_found{$1}++; | ||||
| 				test_line($win32, $_, $tprefix, $1); | ||||
| 				} | ||||
| 			elsif (! /SHAmix\.req$/) | ||||
| 				{ | ||||
| 				print STDERR "WARNING: unrecognized filename $_\n"; | ||||
| 				} | ||||
| 			} | ||||
| 		elsif (-d "$_") | ||||
| 			{ | ||||
| 			if (/$filter.*req$/i) | ||||
| 				{ | ||||
| 				test_dir($win32, $_); | ||||
| 				} | ||||
| 			recurse_test($win32, $tprefix, $filter, $_); | ||||
| 			} | ||||
| 		} | ||||
| 	closedir($dirh); | ||||
| 	} | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub test_dir | ||||
| 	{ | ||||
| 	my ($win32, $req) = @_; | ||||
| 	my $rsp = $req; | ||||
| 	$rsp =~ s/req$/$rspdir/; | ||||
| 	if ($win32) | ||||
| 		{ | ||||
| 		$rsp =~ tr|/|\\|; | ||||
| 		$req =~ tr|/|\\|; | ||||
| 		$bufdir = <<END; | ||||
| 
 | ||||
| echo Running tests in $req | ||||
| if exist "$rsp" rd /s /q "$rsp" | ||||
| md "$rsp" | ||||
| END | ||||
| 		} | ||||
| 	else | ||||
| 		{ | ||||
| 		$bufdir = <<END; | ||||
| 
 | ||||
| echo Running tests in "$req" | ||||
| \$RM "$rsp" | ||||
| \$MKDIR "$rsp" | ||||
| 
 | ||||
| END | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| #-------------------------------- | ||||
| sub test_line | ||||
| 	{ | ||||
| 	my ($win32, $req, $tprefix, $tnam) = @_; | ||||
| 	my $rsp = $req; | ||||
| 	my $tcmd = $fips_tests{$tnam}; | ||||
| 
 | ||||
| 	$bufout .= $bufdir; | ||||
| 	$bufdir = ""; | ||||
| 		 | ||||
| 	$rsp =~ s/req\/([^\/]*).req$/$rspdir\/$1.rsp/; | ||||
| 	if ($tcmd =~ /-f$/) | ||||
| 		{ | ||||
| 		if ($win32) | ||||
| 			{ | ||||
| 			$req =~ tr|/|\\|; | ||||
| 			$rsp =~ tr|/|\\|; | ||||
| 			$bufout .= "$tprefix$tcmd \"$req\" \"$rsp\"\n"; | ||||
| 			$_programs{"$tprefix$tcmd.exe"} = 1; | ||||
| 			} | ||||
| 		else | ||||
| 			{ | ||||
| 			$bufout .= <<END; | ||||
| ${shwrap}\${TPREFIX}$tcmd "$req" "$rsp" || { echo "$req failure" ; exit 1  | ||||
| } | ||||
| END | ||||
| 			$_programs{"${shwrap_prefix}shlib_wrap.sh"} = 1; | ||||
| 			$_programs{"$tprefix$tcmd"} = 1; | ||||
| 			} | ||||
| 		return; | ||||
| 		} | ||||
| 	if ($tcmd =~ /SALT$/) | ||||
| 		{ | ||||
| 		open (IN, $req) || die "Can't Open File $req"; | ||||
| 		my $saltlen; | ||||
| 		while (<IN>) | ||||
| 			{ | ||||
| 			if (/^\s*#\s*salt\s+len:\s+(\d+)\s*$/i) | ||||
| 				{ | ||||
| 				my $sl = $1; | ||||
| 				print STDERR "$req salt length $sl\n" if $debug; | ||||
| 				$tcmd =~ s/SALT$/$sl/; | ||||
| 				$salt_found{"$tnam (salt $sl)"}++; | ||||
| 				last; | ||||
| 				} | ||||
| 			} | ||||
| 		close IN; | ||||
| 		if ($tcmd =~ /SALT$/) | ||||
| 			{ | ||||
| 			die "Can't detect salt length for $req"; | ||||
| 			} | ||||
| 		} | ||||
| 		 | ||||
| 	if ($win32) | ||||
| 		{ | ||||
| 		$req =~ tr|/|\\|; | ||||
| 		$rsp =~ tr|/|\\|; | ||||
| 		$bufout .= "$tprefix$tcmd < \"$req\" > \"$rsp\"\n"; | ||||
| 		$_programs{"$tprefix$tcmd.exe"} = 1; | ||||
| 		} | ||||
| 	else | ||||
| 		{ | ||||
| 		$bufout .= <<END; | ||||
| ${shwrap}\${TPREFIX}$tcmd < "$req" > "$rsp" || { echo "$req failure" ; exit 1; } | ||||
| END | ||||
| 		$_programs{"$tprefix$tcmd"} = 1; | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
|  | @ -0,0 +1,4 @@ | |||
| lib | ||||
| Makefile.save | ||||
| *.flc | ||||
| semantic.cache | ||||
|  | @ -0,0 +1,149 @@ | |||
| #
 | ||||
| # OpenSSL/fips/rand/Makefile
 | ||||
| #
 | ||||
| 
 | ||||
| DIR=	rand | ||||
| TOP=	../.. | ||||
| CC=	cc | ||||
| INCLUDES= | ||||
| CFLAG=-g | ||||
| INSTALL_PREFIX= | ||||
| OPENSSLDIR=     /usr/local/ssl | ||||
| INSTALLTOP=/usr/local/ssl | ||||
| MAKEDEPPROG=	makedepend | ||||
| MAKEDEPEND=	$(TOP)/util/domd $(TOP) -MD $(MAKEDEPPROG) | ||||
| MAKEFILE=	Makefile | ||||
| AR=		ar r | ||||
| 
 | ||||
| CFLAGS= $(INCLUDES) $(CFLAG) | ||||
| 
 | ||||
| GENERAL=Makefile | ||||
| TEST= fips_randtest.c fips_rngvs.c | ||||
| APPS= | ||||
| 
 | ||||
| LIB=$(TOP)/libcrypto.a | ||||
| LIBSRC=fips_rand.c fips_rand_selftest.c | ||||
| LIBOBJ=fips_rand.o fips_rand_selftest.o | ||||
| 
 | ||||
| SRC= $(LIBSRC) | ||||
| 
 | ||||
| EXHEADER= fips_rand.h | ||||
| HEADER=	$(EXHEADER) | ||||
| 
 | ||||
| ALL=    $(GENERAL) $(SRC) $(HEADER) | ||||
| 
 | ||||
| top: | ||||
| 	(cd $(TOP); $(MAKE) DIRS=fips SDIRS=$(DIR) sub_all) | ||||
| 
 | ||||
| all:	lib | ||||
| 
 | ||||
| lib:	$(LIBOBJ) | ||||
| 	@echo $(LIBOBJ) > lib | ||||
| 
 | ||||
| files: | ||||
| 	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO | ||||
| 
 | ||||
| links: | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/include/openssl $(EXHEADER) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/test $(TEST) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/apps $(APPS) | ||||
| 
 | ||||
| install: | ||||
| 	@headerlist="$(EXHEADER)"; for i in $$headerlist; \
 | ||||
| 	do \
 | ||||
| 	  (cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
 | ||||
| 	  chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
 | ||||
| 	done | ||||
| 
 | ||||
| tags: | ||||
| 	ctags $(SRC) | ||||
| 
 | ||||
| tests: | ||||
| 
 | ||||
| Q=../testvectors/rng/req | ||||
| A=../testvectors/rng/rsp | ||||
| 
 | ||||
| fips_test: | ||||
| 	-rm -rf $(A) | ||||
| 	mkdir $(A) | ||||
| 	if [ -f $(Q)/ANSI931_AES128MCT.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs mct < $(Q)/ANSI931_AES128MCT.req > $(A)/ANSI931_AES128MCT.rsp; fi | ||||
| 	if [ -f $(Q)/ANSI931_AES192MCT.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs mct < $(Q)/ANSI931_AES192MCT.req > $(A)/ANSI931_AES192MCT.rsp; fi | ||||
| 	if [ -f $(Q)/ANSI931_AES256MCT.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs mct < $(Q)/ANSI931_AES256MCT.req > $(A)/ANSI931_AES256MCT.rsp; fi | ||||
| 	if [ -f $(Q)/ANSI931_AES128VST.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs vst < $(Q)/ANSI931_AES128VST.req > $(A)/ANSI931_AES128VST.rsp; fi | ||||
| 	if [ -f $(Q)/ANSI931_AES192VST.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs vst < $(Q)/ANSI931_AES192VST.req > $(A)/ANSI931_AES192VST.rsp; fi | ||||
| 	if [ -f $(Q)/ANSI931_AES256VST.req ]; then $(TOP)/util/shlib_wrap.sh $(TOP)/test/fips_rngvs vst < $(Q)/ANSI931_AES256VST.req > $(A)/ANSI931_AES256VST.rsp; fi | ||||
| 
 | ||||
| lint: | ||||
| 	lint -DLINT $(INCLUDES) $(SRC)>fluff | ||||
| 
 | ||||
| depend: | ||||
| 	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(SRC) $(TEST) | ||||
| 
 | ||||
| dclean: | ||||
| 	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new | ||||
| 	mv -f Makefile.new $(MAKEFILE) | ||||
| 
 | ||||
| clean: | ||||
| 	rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff | ||||
| 
 | ||||
| # DO NOT DELETE THIS LINE -- make depend depends on it.
 | ||||
| 
 | ||||
| fips_rand.o: ../../e_os.h ../../include/openssl/aes.h | ||||
| fips_rand.o: ../../include/openssl/bio.h ../../include/openssl/crypto.h | ||||
| fips_rand.o: ../../include/openssl/des.h ../../include/openssl/des_old.h | ||||
| fips_rand.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_rand.o: ../../include/openssl/fips.h ../../include/openssl/fips_rand.h | ||||
| fips_rand.o: ../../include/openssl/lhash.h ../../include/openssl/opensslconf.h | ||||
| fips_rand.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h | ||||
| fips_rand.o: ../../include/openssl/rand.h ../../include/openssl/safestack.h | ||||
| fips_rand.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_rand.o: ../../include/openssl/ui.h ../../include/openssl/ui_compat.h | ||||
| fips_rand.o: ../fips_locl.h fips_rand.c | ||||
| fips_rand_selftest.o: ../../include/openssl/bio.h | ||||
| fips_rand_selftest.o: ../../include/openssl/crypto.h | ||||
| fips_rand_selftest.o: ../../include/openssl/des.h | ||||
| fips_rand_selftest.o: ../../include/openssl/des_old.h | ||||
| fips_rand_selftest.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_rand_selftest.o: ../../include/openssl/fips.h | ||||
| fips_rand_selftest.o: ../../include/openssl/fips_rand.h | ||||
| fips_rand_selftest.o: ../../include/openssl/lhash.h | ||||
| fips_rand_selftest.o: ../../include/openssl/opensslconf.h | ||||
| fips_rand_selftest.o: ../../include/openssl/opensslv.h | ||||
| fips_rand_selftest.o: ../../include/openssl/ossl_typ.h | ||||
| fips_rand_selftest.o: ../../include/openssl/rand.h | ||||
| fips_rand_selftest.o: ../../include/openssl/safestack.h | ||||
| fips_rand_selftest.o: ../../include/openssl/stack.h | ||||
| fips_rand_selftest.o: ../../include/openssl/symhacks.h | ||||
| fips_rand_selftest.o: ../../include/openssl/ui.h | ||||
| fips_rand_selftest.o: ../../include/openssl/ui_compat.h fips_rand_selftest.c | ||||
| fips_randtest.o: ../../e_os.h ../../include/openssl/bio.h | ||||
| fips_randtest.o: ../../include/openssl/bn.h ../../include/openssl/crypto.h | ||||
| fips_randtest.o: ../../include/openssl/des.h ../../include/openssl/des_old.h | ||||
| fips_randtest.o: ../../include/openssl/e_os2.h ../../include/openssl/err.h | ||||
| fips_randtest.o: ../../include/openssl/fips_rand.h | ||||
| fips_randtest.o: ../../include/openssl/lhash.h | ||||
| fips_randtest.o: ../../include/openssl/opensslconf.h | ||||
| fips_randtest.o: ../../include/openssl/opensslv.h | ||||
| fips_randtest.o: ../../include/openssl/ossl_typ.h ../../include/openssl/rand.h | ||||
| fips_randtest.o: ../../include/openssl/safestack.h | ||||
| fips_randtest.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_randtest.o: ../../include/openssl/ui.h ../../include/openssl/ui_compat.h | ||||
| fips_randtest.o: ../fips_utl.h fips_randtest.c | ||||
| fips_rngvs.o: ../../include/openssl/asn1.h ../../include/openssl/bio.h | ||||
| fips_rngvs.o: ../../include/openssl/bn.h ../../include/openssl/buffer.h | ||||
| fips_rngvs.o: ../../include/openssl/conf.h ../../include/openssl/crypto.h | ||||
| fips_rngvs.o: ../../include/openssl/des.h ../../include/openssl/des_old.h | ||||
| fips_rngvs.o: ../../include/openssl/dsa.h ../../include/openssl/e_os2.h | ||||
| fips_rngvs.o: ../../include/openssl/ec.h ../../include/openssl/ecdh.h | ||||
| fips_rngvs.o: ../../include/openssl/ecdsa.h ../../include/openssl/err.h | ||||
| fips_rngvs.o: ../../include/openssl/evp.h ../../include/openssl/fips.h | ||||
| fips_rngvs.o: ../../include/openssl/fips_rand.h ../../include/openssl/lhash.h | ||||
| fips_rngvs.o: ../../include/openssl/obj_mac.h ../../include/openssl/objects.h | ||||
| fips_rngvs.o: ../../include/openssl/opensslconf.h | ||||
| fips_rngvs.o: ../../include/openssl/opensslv.h ../../include/openssl/ossl_typ.h | ||||
| fips_rngvs.o: ../../include/openssl/pkcs7.h ../../include/openssl/rand.h | ||||
| fips_rngvs.o: ../../include/openssl/safestack.h ../../include/openssl/sha.h | ||||
| fips_rngvs.o: ../../include/openssl/stack.h ../../include/openssl/symhacks.h | ||||
| fips_rngvs.o: ../../include/openssl/ui.h ../../include/openssl/ui_compat.h | ||||
| fips_rngvs.o: ../../include/openssl/x509.h ../../include/openssl/x509_vfy.h | ||||
| fips_rngvs.o: ../../include/openssl/x509v3.h ../fips_utl.h fips_rngvs.c | ||||
|  | @ -0,0 +1,412 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| /*
 | ||||
|  * This is a FIPS approved AES PRNG based on ANSI X9.31 A.2.4. | ||||
|  */ | ||||
| 
 | ||||
| #include "e_os.h" | ||||
| 
 | ||||
| /* If we don't define _XOPEN_SOURCE_EXTENDED, struct timeval won't
 | ||||
|    be defined and gettimeofday() won't be declared with strict compilers | ||||
|    like DEC C in ANSI C mode.  */ | ||||
| #ifndef _XOPEN_SOURCE_EXTENDED | ||||
| #define _XOPEN_SOURCE_EXTENDED 1 | ||||
| #endif | ||||
| 
 | ||||
| #include <openssl/rand.h> | ||||
| #include <openssl/aes.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips_rand.h> | ||||
| #ifndef OPENSSL_SYS_WIN32 | ||||
| #include <sys/time.h> | ||||
| #endif | ||||
| #include <assert.h> | ||||
| #ifndef OPENSSL_SYS_WIN32 | ||||
| # ifdef OPENSSL_UNISTD | ||||
| #  include OPENSSL_UNISTD | ||||
| # else | ||||
| #  include <unistd.h> | ||||
| # endif | ||||
| #endif | ||||
| #include <string.h> | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_locl.h" | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| void *OPENSSL_stderr(void); | ||||
| 
 | ||||
| #define AES_BLOCK_LENGTH	16 | ||||
| 
 | ||||
| 
 | ||||
| /* AES FIPS PRNG implementation */ | ||||
| 
 | ||||
| typedef struct  | ||||
| 	{ | ||||
| 	int seeded; | ||||
| 	int keyed; | ||||
| 	int test_mode; | ||||
| 	int second; | ||||
| 	int error; | ||||
| 	unsigned long counter; | ||||
| 	AES_KEY ks; | ||||
| 	int vpos; | ||||
| 	/* Temporary storage for key if it equals seed length */ | ||||
| 	unsigned char tmp_key[AES_BLOCK_LENGTH]; | ||||
| 	unsigned char V[AES_BLOCK_LENGTH]; | ||||
| 	unsigned char DT[AES_BLOCK_LENGTH]; | ||||
| 	unsigned char last[AES_BLOCK_LENGTH]; | ||||
| 	} FIPS_PRNG_CTX; | ||||
| 
 | ||||
| static FIPS_PRNG_CTX sctx; | ||||
| 
 | ||||
| static int fips_prng_fail = 0; | ||||
| 
 | ||||
| void FIPS_rng_stick(void) | ||||
| 	{ | ||||
| 	fips_prng_fail = 1; | ||||
| 	} | ||||
| 
 | ||||
| static void fips_rand_prng_reset(FIPS_PRNG_CTX *ctx) | ||||
| 	{ | ||||
| 	ctx->seeded = 0; | ||||
| 	ctx->keyed = 0; | ||||
| 	ctx->test_mode = 0; | ||||
| 	ctx->counter = 0; | ||||
| 	ctx->second = 0; | ||||
| 	ctx->error = 0; | ||||
| 	ctx->vpos = 0; | ||||
| 	OPENSSL_cleanse(ctx->V, AES_BLOCK_LENGTH); | ||||
| 	OPENSSL_cleanse(&ctx->ks, sizeof(AES_KEY)); | ||||
| 	} | ||||
| 	 | ||||
| 
 | ||||
| static int fips_set_prng_key(FIPS_PRNG_CTX *ctx, | ||||
| 			const unsigned char *key, unsigned int keylen) | ||||
| 	{ | ||||
| 	FIPS_selftest_check(); | ||||
| 	if (keylen != 16 && keylen != 24 && keylen != 32) | ||||
| 		{ | ||||
| 		/* error: invalid key size */ | ||||
| 		return 0; | ||||
| 		} | ||||
| 	AES_set_encrypt_key(key, keylen << 3, &ctx->ks); | ||||
| 	if (keylen == 16) | ||||
| 		{ | ||||
| 		memcpy(ctx->tmp_key, key, 16); | ||||
| 		ctx->keyed = 2; | ||||
| 		} | ||||
| 	else | ||||
| 		ctx->keyed = 1; | ||||
| 	ctx->seeded = 0; | ||||
| 	ctx->second = 0; | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| static int fips_set_prng_seed(FIPS_PRNG_CTX *ctx, | ||||
| 			const unsigned char *seed, unsigned int seedlen) | ||||
| 	{ | ||||
| 	unsigned int i; | ||||
| 	if (!ctx->keyed) | ||||
| 		return 0; | ||||
| 	/* In test mode seed is just supplied data */ | ||||
| 	if (ctx->test_mode) | ||||
| 		{ | ||||
| 		if (seedlen != AES_BLOCK_LENGTH) | ||||
| 			return 0; | ||||
| 		memcpy(ctx->V, seed, AES_BLOCK_LENGTH); | ||||
| 		ctx->seeded = 1; | ||||
| 		return 1; | ||||
| 		} | ||||
| 	/* Outside test mode XOR supplied data with existing seed */ | ||||
| 	for (i = 0; i < seedlen; i++) | ||||
| 		{ | ||||
| 		ctx->V[ctx->vpos++] ^= seed[i]; | ||||
| 		if (ctx->vpos == AES_BLOCK_LENGTH) | ||||
| 			{ | ||||
| 			ctx->vpos = 0; | ||||
| 			/* Special case if first seed and key length equals
 | ||||
|  			 * block size check key and seed do not match. | ||||
|  			 */  | ||||
| 			if (ctx->keyed == 2) | ||||
| 				{ | ||||
| 				if (!memcmp(ctx->tmp_key, ctx->V, 16)) | ||||
| 					{ | ||||
| 					RANDerr(RAND_F_FIPS_SET_PRNG_SEED, | ||||
| 						RAND_R_PRNG_SEED_MUST_NOT_MATCH_KEY); | ||||
| 					return 0; | ||||
| 					} | ||||
| 				OPENSSL_cleanse(ctx->tmp_key, 16); | ||||
| 				ctx->keyed = 1; | ||||
| 				} | ||||
| 			ctx->seeded = 1; | ||||
| 			} | ||||
| 		} | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| static int fips_set_test_mode(FIPS_PRNG_CTX *ctx) | ||||
| 	{ | ||||
| 	if (ctx->keyed) | ||||
| 		{ | ||||
| 		RANDerr(RAND_F_FIPS_SET_TEST_MODE,RAND_R_PRNG_KEYED); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	ctx->test_mode = 1; | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_rand_test_mode(void) | ||||
| 	{ | ||||
| 	return fips_set_test_mode(&sctx); | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_rand_set_dt(unsigned char *dt) | ||||
| 	{ | ||||
| 	if (!sctx.test_mode) | ||||
| 		{ | ||||
| 		RANDerr(RAND_F_FIPS_RAND_SET_DT,RAND_R_NOT_IN_TEST_MODE); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	memcpy(sctx.DT, dt, AES_BLOCK_LENGTH); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| static void fips_get_dt(FIPS_PRNG_CTX *ctx) | ||||
|     { | ||||
| #ifdef OPENSSL_SYS_WIN32 | ||||
| 	FILETIME ft; | ||||
| #else | ||||
| 	struct timeval tv; | ||||
| #endif | ||||
| 	unsigned char *buf = ctx->DT; | ||||
| 
 | ||||
| #ifndef GETPID_IS_MEANINGLESS | ||||
| 	unsigned long pid; | ||||
| #endif | ||||
| 
 | ||||
| #ifdef OPENSSL_SYS_WIN32 | ||||
| 	GetSystemTimeAsFileTime(&ft); | ||||
| 	buf[0] = (unsigned char) (ft.dwHighDateTime & 0xff); | ||||
| 	buf[1] = (unsigned char) ((ft.dwHighDateTime >> 8) & 0xff); | ||||
| 	buf[2] = (unsigned char) ((ft.dwHighDateTime >> 16) & 0xff); | ||||
| 	buf[3] = (unsigned char) ((ft.dwHighDateTime >> 24) & 0xff); | ||||
| 	buf[4] = (unsigned char) (ft.dwLowDateTime & 0xff); | ||||
| 	buf[5] = (unsigned char) ((ft.dwLowDateTime >> 8) & 0xff); | ||||
| 	buf[6] = (unsigned char) ((ft.dwLowDateTime >> 16) & 0xff); | ||||
| 	buf[7] = (unsigned char) ((ft.dwLowDateTime >> 24) & 0xff); | ||||
| #else | ||||
| 	gettimeofday(&tv,NULL); | ||||
| 	buf[0] = (unsigned char) (tv.tv_sec & 0xff); | ||||
| 	buf[1] = (unsigned char) ((tv.tv_sec >> 8) & 0xff); | ||||
| 	buf[2] = (unsigned char) ((tv.tv_sec >> 16) & 0xff); | ||||
| 	buf[3] = (unsigned char) ((tv.tv_sec >> 24) & 0xff); | ||||
| 	buf[4] = (unsigned char) (tv.tv_usec & 0xff); | ||||
| 	buf[5] = (unsigned char) ((tv.tv_usec >> 8) & 0xff); | ||||
| 	buf[6] = (unsigned char) ((tv.tv_usec >> 16) & 0xff); | ||||
| 	buf[7] = (unsigned char) ((tv.tv_usec >> 24) & 0xff); | ||||
| #endif | ||||
| 	buf[8] = (unsigned char) (ctx->counter & 0xff); | ||||
| 	buf[9] = (unsigned char) ((ctx->counter >> 8) & 0xff); | ||||
| 	buf[10] = (unsigned char) ((ctx->counter >> 16) & 0xff); | ||||
| 	buf[11] = (unsigned char) ((ctx->counter >> 24) & 0xff); | ||||
| 
 | ||||
| 	ctx->counter++; | ||||
| 
 | ||||
| 
 | ||||
| #ifndef GETPID_IS_MEANINGLESS | ||||
| 	pid=(unsigned long)getpid(); | ||||
| 	buf[12] = (unsigned char) (pid & 0xff); | ||||
| 	buf[13] = (unsigned char) ((pid >> 8) & 0xff); | ||||
| 	buf[14] = (unsigned char) ((pid >> 16) & 0xff); | ||||
| 	buf[15] = (unsigned char) ((pid >> 24) & 0xff); | ||||
| #endif | ||||
|     } | ||||
| 
 | ||||
| static int fips_rand(FIPS_PRNG_CTX *ctx, | ||||
| 			unsigned char *out, unsigned int outlen) | ||||
| 	{ | ||||
| 	unsigned char R[AES_BLOCK_LENGTH], I[AES_BLOCK_LENGTH]; | ||||
| 	unsigned char tmp[AES_BLOCK_LENGTH]; | ||||
| 	int i; | ||||
| 	if (ctx->error) | ||||
| 		{ | ||||
| 		RANDerr(RAND_F_FIPS_RAND,RAND_R_PRNG_ERROR); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	if (!ctx->keyed) | ||||
| 		{ | ||||
| 		RANDerr(RAND_F_FIPS_RAND,RAND_R_NO_KEY_SET); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	if (!ctx->seeded) | ||||
| 		{ | ||||
| 		RANDerr(RAND_F_FIPS_RAND,RAND_R_PRNG_NOT_SEEDED); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	for (;;) | ||||
| 		{ | ||||
| 		if (!ctx->test_mode) | ||||
| 			fips_get_dt(ctx); | ||||
| 		AES_encrypt(ctx->DT, I, &ctx->ks); | ||||
| 		for (i = 0; i < AES_BLOCK_LENGTH; i++) | ||||
| 			tmp[i] = I[i] ^ ctx->V[i]; | ||||
| 		AES_encrypt(tmp, R, &ctx->ks); | ||||
| 		for (i = 0; i < AES_BLOCK_LENGTH; i++) | ||||
| 			tmp[i] = R[i] ^ I[i]; | ||||
| 		AES_encrypt(tmp, ctx->V, &ctx->ks); | ||||
| 		/* Continuous PRNG test */ | ||||
| 		if (ctx->second) | ||||
| 			{ | ||||
| 			if (fips_prng_fail) | ||||
| 				memcpy(ctx->last, R, AES_BLOCK_LENGTH); | ||||
| 			if (!memcmp(R, ctx->last, AES_BLOCK_LENGTH)) | ||||
| 				{ | ||||
| 	    			RANDerr(RAND_F_FIPS_RAND,RAND_R_PRNG_STUCK); | ||||
| 				ctx->error = 1; | ||||
| 				fips_set_selftest_fail(); | ||||
| 				return 0; | ||||
| 				} | ||||
| 			} | ||||
| 		memcpy(ctx->last, R, AES_BLOCK_LENGTH); | ||||
| 		if (!ctx->second) | ||||
| 			{ | ||||
| 			ctx->second = 1; | ||||
| 			if (!ctx->test_mode) | ||||
| 				continue; | ||||
| 			} | ||||
| 
 | ||||
| 		if (outlen <= AES_BLOCK_LENGTH) | ||||
| 			{ | ||||
| 			memcpy(out, R, outlen); | ||||
| 			break; | ||||
| 			} | ||||
| 
 | ||||
| 		memcpy(out, R, AES_BLOCK_LENGTH); | ||||
| 		out += AES_BLOCK_LENGTH; | ||||
| 		outlen -= AES_BLOCK_LENGTH; | ||||
| 		} | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| 
 | ||||
| int FIPS_rand_set_key(const unsigned char *key, int keylen) | ||||
| 	{ | ||||
| 	int ret; | ||||
| 	CRYPTO_w_lock(CRYPTO_LOCK_RAND); | ||||
| 	ret = fips_set_prng_key(&sctx, key, keylen); | ||||
| 	CRYPTO_w_unlock(CRYPTO_LOCK_RAND); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_rand_seed(const void *seed, int seedlen) | ||||
| 	{ | ||||
| 	int ret; | ||||
| 	CRYPTO_w_lock(CRYPTO_LOCK_RAND); | ||||
| 	ret = fips_set_prng_seed(&sctx, seed, seedlen); | ||||
| 	CRYPTO_w_unlock(CRYPTO_LOCK_RAND); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| 
 | ||||
| int FIPS_rand_bytes(unsigned char *out, int count) | ||||
| 	{ | ||||
| 	int ret; | ||||
| 	CRYPTO_w_lock(CRYPTO_LOCK_RAND); | ||||
| 	ret = fips_rand(&sctx, out, count); | ||||
| 	CRYPTO_w_unlock(CRYPTO_LOCK_RAND); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_rand_status(void) | ||||
| 	{ | ||||
| 	int ret; | ||||
| 	CRYPTO_r_lock(CRYPTO_LOCK_RAND); | ||||
| 	ret = sctx.seeded; | ||||
| 	CRYPTO_r_unlock(CRYPTO_LOCK_RAND); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_rand_reset(void) | ||||
| 	{ | ||||
| 	CRYPTO_w_lock(CRYPTO_LOCK_RAND); | ||||
| 	fips_rand_prng_reset(&sctx); | ||||
| 	CRYPTO_w_unlock(CRYPTO_LOCK_RAND); | ||||
| 	} | ||||
| 
 | ||||
| static int fips_do_rand_seed(const void *seed, int seedlen) | ||||
| 	{ | ||||
| 	FIPS_rand_seed(seed, seedlen); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| static int fips_do_rand_add(const void *seed, int seedlen, | ||||
| 					double add_entropy) | ||||
| 	{ | ||||
| 	FIPS_rand_seed(seed, seedlen); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| static const RAND_METHOD rand_fips_meth= | ||||
|     { | ||||
|     fips_do_rand_seed, | ||||
|     FIPS_rand_bytes, | ||||
|     FIPS_rand_reset, | ||||
|     fips_do_rand_add, | ||||
|     FIPS_rand_bytes, | ||||
|     FIPS_rand_status | ||||
|     }; | ||||
| 
 | ||||
| const RAND_METHOD *FIPS_rand_method(void) | ||||
| { | ||||
|   return &rand_fips_meth; | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,77 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #ifndef HEADER_FIPS_RAND_H | ||||
| #define HEADER_FIPS_RAND_H | ||||
| 
 | ||||
| #include "des.h" | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| extern "C" { | ||||
| #endif | ||||
| 
 | ||||
| int FIPS_rand_set_key(const unsigned char *key, int keylen); | ||||
| int FIPS_rand_seed(const void *buf, int num); | ||||
| int FIPS_rand_bytes(unsigned char *out, int outlen); | ||||
| 
 | ||||
| int FIPS_rand_test_mode(void); | ||||
| void FIPS_rand_reset(void); | ||||
| int FIPS_rand_set_dt(unsigned char *dt); | ||||
| 
 | ||||
| int FIPS_rand_status(void); | ||||
| 
 | ||||
| const RAND_METHOD *FIPS_rand_method(void); | ||||
| 
 | ||||
| #ifdef  __cplusplus | ||||
| } | ||||
| #endif | ||||
| #endif | ||||
| #endif | ||||
|  | @ -0,0 +1,371 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/rand.h> | ||||
| #include <openssl/fips_rand.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
| typedef struct | ||||
| 	{ | ||||
| 	unsigned char DT[16]; | ||||
| 	unsigned char V[16]; | ||||
| 	unsigned char R[16]; | ||||
| 	} AES_PRNG_TV; | ||||
| 
 | ||||
| /* The following test vectors are taken directly from the RGNVS spec */ | ||||
| 
 | ||||
| static unsigned char aes_128_key[16] = | ||||
| 		{0xf3,0xb1,0x66,0x6d,0x13,0x60,0x72,0x42, | ||||
| 		 0xed,0x06,0x1c,0xab,0xb8,0xd4,0x62,0x02}; | ||||
| 
 | ||||
| static AES_PRNG_TV aes_128_tv[] = { | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x22,0xf9}, | ||||
| 				/* V */ | ||||
| 		{0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x59,0x53,0x1e,0xd1,0x3b,0xb0,0xc0,0x55, | ||||
| 		 0x84,0x79,0x66,0x85,0xc1,0x2f,0x76,0x41} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x22,0xfa}, | ||||
| 				/* V */ | ||||
| 		{0xc0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x7c,0x22,0x2c,0xf4,0xca,0x8f,0xa2,0x4c, | ||||
| 		 0x1c,0x9c,0xb6,0x41,0xa9,0xf3,0x22,0x0d} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x22,0xfb}, | ||||
| 				/* V */ | ||||
| 		{0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x8a,0xaa,0x00,0x39,0x66,0x67,0x5b,0xe5, | ||||
| 		 0x29,0x14,0x28,0x81,0xa9,0x4d,0x4e,0xc7} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x22,0xfc}, | ||||
| 				/* V */ | ||||
| 		{0xf0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x88,0xdd,0xa4,0x56,0x30,0x24,0x23,0xe5, | ||||
| 		 0xf6,0x9d,0xa5,0x7e,0x7b,0x95,0xc7,0x3a} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x22,0xfd}, | ||||
| 				/* V */ | ||||
| 		{0xf8,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x05,0x25,0x92,0x46,0x61,0x79,0xd2,0xcb, | ||||
| 		 0x78,0xc4,0x0b,0x14,0x0a,0x5a,0x9a,0xc8} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x23,0x77}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xfe}, | ||||
| 				/* R */ | ||||
| 		{0x0d,0xd5,0xa0,0x36,0x7a,0x59,0x26,0xbc, | ||||
| 		 0x48,0xd9,0x38,0xbf,0xf0,0x85,0x8f,0xea} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xe6,0xb3,0xbe,0x78,0x2a,0x23,0xfa,0x62, | ||||
| 		 0xd7,0x1d,0x4a,0xfb,0xb0,0xe9,0x23,0x78}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}, | ||||
| 				/* R */ | ||||
| 		{0xae,0x53,0x87,0xee,0x8c,0xd9,0x12,0xf5, | ||||
| 		 0x73,0x53,0xae,0x03,0xf9,0xd5,0x13,0x33} | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| static unsigned char aes_192_key[24] = | ||||
| 		{0x15,0xd8,0x78,0x0d,0x62,0xd3,0x25,0x6e, | ||||
| 		 0x44,0x64,0x10,0x13,0x60,0x2b,0xa9,0xbc, | ||||
| 		 0x4a,0xfb,0xca,0xeb,0x4c,0x8b,0x99,0x3b}; | ||||
| 
 | ||||
| static AES_PRNG_TV aes_192_tv[] = { | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0x4b}, | ||||
| 				/* V */ | ||||
| 		{0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x17,0x07,0xd5,0x28,0x19,0x79,0x1e,0xef, | ||||
| 		 0xa5,0x0c,0xbf,0x25,0xe5,0x56,0xb4,0x93} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0x4c}, | ||||
| 				/* V */ | ||||
| 		{0xc0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x92,0x8d,0xbe,0x07,0xdd,0xc7,0x58,0xc0, | ||||
| 		 0x6f,0x35,0x41,0x9b,0x17,0xc9,0xbd,0x9b} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0x4d}, | ||||
| 				/* V */ | ||||
| 		{0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0xd5,0xde,0xf4,0x50,0xf3,0xb7,0x10,0x4e, | ||||
| 		 0xb8,0xc6,0xf8,0xcf,0xe2,0xb1,0xca,0xa2} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0x4e}, | ||||
| 				/* V */ | ||||
| 		{0xf0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0xce,0x29,0x08,0x43,0xfc,0x34,0x41,0xe7, | ||||
| 		 0x47,0x8f,0xb3,0x66,0x2b,0x46,0xb1,0xbb} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0x4f}, | ||||
| 				/* V */ | ||||
| 		{0xf8,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0xb3,0x26,0x0f,0xf5,0xd6,0xca,0xa8,0xbf, | ||||
| 		 0x89,0xb8,0x5e,0x2f,0x22,0x56,0x92,0x2f} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0xc9}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xfe}, | ||||
| 				/* R */ | ||||
| 		{0x05,0xeb,0x18,0x52,0x34,0x43,0x00,0x43, | ||||
| 		 0x6e,0x5a,0xa5,0xfe,0x7b,0x32,0xc4,0x2d} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0x3f,0xd8,0xff,0xe8,0x80,0x69,0x8b,0xc1, | ||||
| 		 0xbf,0x99,0x7d,0xa4,0x24,0x78,0xf3,0xca}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}, | ||||
| 				/* R */ | ||||
| 		{0x15,0x3c,0xe8,0xd1,0x04,0xc7,0xad,0x50, | ||||
| 		 0x0b,0xf0,0x07,0x16,0xe7,0x56,0x7a,0xea} | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| static unsigned char aes_256_key[32] = | ||||
| 		{0x6d,0x14,0x06,0x6c,0xb6,0xd8,0x21,0x2d, | ||||
| 		 0x82,0x8d,0xfa,0xf2,0x7a,0x03,0xb7,0x9f, | ||||
| 		 0x0c,0xc7,0x3e,0xcd,0x76,0xeb,0xee,0xb5, | ||||
| 		 0x21,0x05,0x8c,0x4f,0x31,0x7a,0x80,0xbb}; | ||||
| 
 | ||||
| static AES_PRNG_TV aes_256_tv[] = { | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9e,0x88}, | ||||
| 				/* V */ | ||||
| 		{0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x35,0xc7,0xef,0xa7,0x78,0x4d,0x29,0xbc, | ||||
| 		 0x82,0x79,0x99,0xfb,0xd0,0xb3,0x3b,0x72} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9e,0x89}, | ||||
| 				/* V */ | ||||
| 		{0xc0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x6c,0xf4,0x42,0x5d,0xc7,0x04,0x1a,0x41, | ||||
| 		 0x28,0x2a,0x78,0xa9,0xb0,0x12,0xc4,0x95} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9e,0x8a}, | ||||
| 				/* V */ | ||||
| 		{0xe0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x16,0x90,0xa4,0xff,0x7b,0x7e,0xb9,0x30, | ||||
| 		 0xdb,0x67,0x4b,0xac,0x2d,0xe1,0xd1,0x75} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9e,0x8b}, | ||||
| 				/* V */ | ||||
| 		{0xf0,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x14,0x6f,0xf5,0x95,0xa1,0x46,0x65,0x30, | ||||
| 		 0xbc,0x57,0xe2,0x4a,0xf7,0x45,0x62,0x05} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9e,0x8c}, | ||||
| 				/* V */ | ||||
| 		{0xf8,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||||
| 		 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, | ||||
| 				/* R */ | ||||
| 		{0x96,0xe2,0xb4,0x1e,0x66,0x5e,0x0f,0xa4, | ||||
| 		 0xc5,0xcd,0xa2,0x07,0xcc,0xb7,0x94,0x40} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9f,0x06}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xfe}, | ||||
| 				/* R */ | ||||
| 		{0x61,0xce,0x1d,0x6a,0x48,0x75,0x97,0x28, | ||||
| 		 0x4b,0x41,0xde,0x18,0x44,0x4f,0x56,0xec} | ||||
| 	}, | ||||
| 	{ | ||||
| 				/* DT */ | ||||
| 		{0xda,0x3a,0x41,0xec,0x1d,0xa3,0xb0,0xd5, | ||||
| 		 0xf2,0xa9,0x4e,0x34,0x74,0x8e,0x9f,0x07}, | ||||
| 				/* V */ | ||||
| 		{0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff, | ||||
| 		 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}, | ||||
| 				/* R */ | ||||
| 		{0x52,0x89,0x59,0x79,0x2d,0xaa,0x28,0xb3, | ||||
| 		 0xb0,0x8a,0x3e,0x70,0xfa,0x71,0x59,0x84} | ||||
| 	}, | ||||
| }; | ||||
| 
 | ||||
| 
 | ||||
| void FIPS_corrupt_rng() | ||||
|     { | ||||
|     aes_192_tv[0].V[0]++; | ||||
|     } | ||||
| 
 | ||||
| #define fips_rand_test(key, tv) \ | ||||
| 	do_rand_test(key, sizeof key, tv, sizeof(tv)/sizeof(AES_PRNG_TV)) | ||||
| 
 | ||||
| static int do_rand_test(unsigned char *key, int keylen, | ||||
| 			AES_PRNG_TV *tv, int ntv) | ||||
| 	{ | ||||
| 	unsigned char R[16]; | ||||
| 	int i; | ||||
| 	if (!FIPS_rand_set_key(key, keylen)) | ||||
| 		return 0; | ||||
| 	for (i = 0; i < ntv; i++) | ||||
| 		{ | ||||
| 		FIPS_rand_seed(tv[i].V, 16); | ||||
| 		FIPS_rand_set_dt(tv[i].DT); | ||||
| 		FIPS_rand_bytes(R, 16); | ||||
| 		if (memcmp(R, tv[i].R, 16)) | ||||
| 			return 0; | ||||
| 		} | ||||
| 	return 1; | ||||
| 	} | ||||
| 	 | ||||
| 
 | ||||
| int FIPS_selftest_rng() | ||||
| 	{ | ||||
| 	FIPS_rand_reset(); | ||||
| 	if (!FIPS_rand_test_mode()) | ||||
| 		{ | ||||
| 		FIPSerr(FIPS_F_FIPS_SELFTEST_RNG,FIPS_R_SELFTEST_FAILED); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	if (!fips_rand_test(aes_128_key,aes_128_tv) | ||||
| 		|| !fips_rand_test(aes_192_key, aes_192_tv) | ||||
| 		|| !fips_rand_test(aes_256_key, aes_256_tv)) | ||||
| 		{ | ||||
| 		FIPSerr(FIPS_F_FIPS_SELFTEST_RNG,FIPS_R_SELFTEST_FAILED); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	FIPS_rand_reset(); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,250 @@ | |||
| /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
 | ||||
|  * All rights reserved. | ||||
|  * | ||||
|  * This package is an SSL implementation written | ||||
|  * by Eric Young (eay@cryptsoft.com). | ||||
|  * The implementation was written so as to conform with Netscapes SSL. | ||||
|  *  | ||||
|  * This library is free for commercial and non-commercial use as long as | ||||
|  * the following conditions are aheared to.  The following conditions | ||||
|  * apply to all code found in this distribution, be it the RC4, RSA, | ||||
|  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation | ||||
|  * included with this distribution is covered by the same copyright terms | ||||
|  * except that the holder is Tim Hudson (tjh@cryptsoft.com). | ||||
|  *  | ||||
|  * Copyright remains Eric Young's, and as such any Copyright notices in | ||||
|  * the code are not to be removed. | ||||
|  * If this package is used in a product, Eric Young should be given attribution | ||||
|  * as the author of the parts of the library used. | ||||
|  * This can be in the form of a textual message at program startup or | ||||
|  * in documentation (online or textual) provided with the package. | ||||
|  *  | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * 1. Redistributions of source code must retain the copyright | ||||
|  *    notice, this list of conditions and the following disclaimer. | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in the | ||||
|  *    documentation and/or other materials provided with the distribution. | ||||
|  * 3. All advertising materials mentioning features or use of this software | ||||
|  *    must display the following acknowledgement: | ||||
|  *    "This product includes cryptographic software written by | ||||
|  *     Eric Young (eay@cryptsoft.com)" | ||||
|  *    The word 'cryptographic' can be left out if the rouines from the library | ||||
|  *    being used are not cryptographic related :-). | ||||
|  * 4. If you include any Windows specific code (or a derivative thereof) from  | ||||
|  *    the apps directory (application code) you must include an acknowledgement: | ||||
|  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | ||||
|  *  | ||||
|  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND | ||||
|  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||||
|  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | ||||
|  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||||
|  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||||
|  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||||
|  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||||
|  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||||
|  * SUCH DAMAGE. | ||||
|  *  | ||||
|  * The licence and distribution terms for any publically available version or | ||||
|  * derivative of this code cannot be changed.  i.e. this code cannot simply be | ||||
|  * copied and put under another distribution licence | ||||
|  * [including the GNU Public Licence.] | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #include <ctype.h> | ||||
| #include <openssl/rand.h> | ||||
| #include <openssl/fips_rand.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #include "e_os.h" | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS RAND support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| typedef struct | ||||
| 	{ | ||||
| 	unsigned char DT[16]; | ||||
| 	unsigned char V[16]; | ||||
| 	unsigned char R[16]; | ||||
| 	} AES_PRNG_MCT; | ||||
| 
 | ||||
| static unsigned char aes_128_mct_key[16] = | ||||
| 	{0x9f,0x5b,0x51,0x20,0x0b,0xf3,0x34,0xb5, | ||||
| 	 0xd8,0x2b,0xe8,0xc3,0x72,0x55,0xc8,0x48}; | ||||
| 
 | ||||
| static AES_PRNG_MCT aes_128_mct_tv = { | ||||
| 			/* DT */ | ||||
| 	{0x63,0x76,0xbb,0xe5,0x29,0x02,0xba,0x3b, | ||||
| 	 0x67,0xc9,0x25,0xfa,0x70,0x1f,0x11,0xac}, | ||||
| 			/* V */ | ||||
| 	{0x57,0x2c,0x8e,0x76,0x87,0x26,0x47,0x97, | ||||
| 	 0x7e,0x74,0xfb,0xdd,0xc4,0x95,0x01,0xd1}, | ||||
| 			/* R */ | ||||
| 	{0x48,0xe9,0xbd,0x0d,0x06,0xee,0x18,0xfb, | ||||
| 	 0xe4,0x57,0x90,0xd5,0xc3,0xfc,0x9b,0x73} | ||||
| }; | ||||
| 
 | ||||
| static unsigned char aes_192_mct_key[24] = | ||||
| 	{0xb7,0x6c,0x34,0xd1,0x09,0x67,0xab,0x73, | ||||
| 	 0x4d,0x5a,0xd5,0x34,0x98,0x16,0x0b,0x91, | ||||
| 	 0xbc,0x35,0x51,0x16,0x6b,0xae,0x93,0x8a}; | ||||
| 
 | ||||
| static AES_PRNG_MCT aes_192_mct_tv = { | ||||
| 			/* DT */ | ||||
| 	{0x84,0xce,0x22,0x7d,0x91,0x5a,0xa3,0xc9, | ||||
| 	 0x84,0x3c,0x0a,0xb3,0xa9,0x63,0x15,0x52}, | ||||
| 			/* V */ | ||||
| 	{0xb6,0xaf,0xe6,0x8f,0x99,0x9e,0x90,0x64, | ||||
| 	 0xdd,0xc7,0x7a,0xc1,0xbb,0x90,0x3a,0x6d}, | ||||
| 			/* R */ | ||||
| 	{0xfc,0x85,0x60,0x9a,0x29,0x6f,0xef,0x21, | ||||
| 	 0xdd,0x86,0x20,0x32,0x8a,0x29,0x6f,0x47} | ||||
| }; | ||||
| 
 | ||||
| static unsigned char aes_256_mct_key[32] = | ||||
| 	{0x9b,0x05,0xc8,0x68,0xff,0x47,0xf8,0x3a, | ||||
| 	 0xa6,0x3a,0xa8,0xcb,0x4e,0x71,0xb2,0xe0, | ||||
| 	 0xb8,0x7e,0xf1,0x37,0xb6,0xb4,0xf6,0x6d, | ||||
| 	 0x86,0x32,0xfc,0x1f,0x5e,0x1d,0x1e,0x50}; | ||||
| 
 | ||||
| static AES_PRNG_MCT aes_256_mct_tv = { | ||||
| 			/* DT */ | ||||
| 	{0x31,0x6e,0x35,0x9a,0xb1,0x44,0xf0,0xee, | ||||
| 	 0x62,0x6d,0x04,0x46,0xe0,0xa3,0x92,0x4c}, | ||||
| 			/* V */ | ||||
| 	{0x4f,0xcd,0xc1,0x87,0x82,0x1f,0x4d,0xa1, | ||||
| 	 0x3e,0x0e,0x56,0x44,0x59,0xe8,0x83,0xca}, | ||||
| 			/* R */ | ||||
| 	{0xc8,0x87,0xc2,0x61,0x5b,0xd0,0xb9,0xe1, | ||||
| 	 0xe7,0xf3,0x8b,0xd7,0x5b,0xd5,0xf1,0x8d} | ||||
| }; | ||||
| 
 | ||||
| static void dump(const unsigned char *b,int n) | ||||
|     { | ||||
|     while(n-- > 0) | ||||
| 	{ | ||||
| 	printf(" %02x",*b++); | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| static void compare(const unsigned char *result,const unsigned char *expected, | ||||
| 		    int n) | ||||
|     { | ||||
|     int i; | ||||
| 
 | ||||
|     for(i=0 ; i < n ; ++i) | ||||
| 	if(result[i] != expected[i]) | ||||
| 	    { | ||||
| 	    puts("Random test failed, got:"); | ||||
| 	    dump(result,n); | ||||
| 	    puts("\n               expected:"); | ||||
| 	    dump(expected,n); | ||||
| 	    putchar('\n'); | ||||
| 	    EXIT(1); | ||||
| 	    } | ||||
|     } | ||||
| 
 | ||||
| 
 | ||||
| static void run_test(unsigned char *key, int keylen, AES_PRNG_MCT *tv) | ||||
|     { | ||||
|     unsigned char buf[16], dt[16]; | ||||
|     int i, j; | ||||
|     FIPS_rand_reset(); | ||||
|     FIPS_rand_test_mode(); | ||||
|     FIPS_rand_set_key(key, keylen); | ||||
|     FIPS_rand_seed(tv->V, 16); | ||||
|     memcpy(dt, tv->DT, 16); | ||||
|     for (i = 0; i < 10000; i++) | ||||
| 	{ | ||||
|     	FIPS_rand_set_dt(dt); | ||||
| 	FIPS_rand_bytes(buf, 16); | ||||
| 	/* Increment DT */ | ||||
| 	for (j = 15; j >= 0; j--) | ||||
| 		{ | ||||
| 		dt[j]++; | ||||
| 		if (dt[j]) | ||||
| 			break; | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
|     compare(buf,tv->R, 16); | ||||
|     } | ||||
| 
 | ||||
| int main() | ||||
| 	{ | ||||
| 	fips_set_error_print(); | ||||
| 	run_test(aes_128_mct_key, 16, &aes_128_mct_tv); | ||||
| 	printf("FIPS PRNG test 1 done\n"); | ||||
| 	run_test(aes_192_mct_key, 24, &aes_192_mct_tv); | ||||
| 	printf("FIPS PRNG test 2 done\n"); | ||||
| 	run_test(aes_256_mct_key, 32, &aes_256_mct_tv); | ||||
| 	printf("FIPS PRNG test 3 done\n"); | ||||
| 	return 0; | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,227 @@ | |||
| /*
 | ||||
|  * Crude test driver for processing the VST and MCT testvector files | ||||
|  * generated by the CMVP RNGVS product. | ||||
|  * | ||||
|  * Note the input files are assumed to have a _very_ specific format | ||||
|  * as described in the NIST document "The Random Number Generator | ||||
|  * Validation System (RNGVS)", May 25, 2004. | ||||
|  * | ||||
|  */ | ||||
| #include <openssl/opensslconf.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| #include <stdio.h> | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| { | ||||
|     printf("No FIPS RNG support\n"); | ||||
|     return 0; | ||||
| } | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/dsa.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/rand.h> | ||||
| #include <openssl/fips_rand.h> | ||||
| #include <openssl/x509v3.h> | ||||
| #include <string.h> | ||||
| #include <ctype.h> | ||||
| 
 | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| static void vst() | ||||
|     { | ||||
|     unsigned char *key = NULL; | ||||
|     unsigned char *v = NULL; | ||||
|     unsigned char *dt = NULL; | ||||
|     unsigned char ret[16]; | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     long i, keylen; | ||||
| 
 | ||||
|     keylen = 0; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	fputs(buf,stdout); | ||||
| 	if(!strncmp(buf,"[AES 128-Key]", 13)) | ||||
| 		keylen = 16; | ||||
| 	else if(!strncmp(buf,"[AES 192-Key]", 13)) | ||||
| 		keylen = 24; | ||||
| 	else if(!strncmp(buf,"[AES 256-Key]", 13)) | ||||
| 		keylen = 32; | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		continue; | ||||
| 	if(!strcmp(keyword,"Key")) | ||||
| 	    { | ||||
| 	    key=hex2bin_m(value,&i); | ||||
| 	    if (i != keylen) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid key length, expecting %ld\n", keylen); | ||||
| 		return; | ||||
| 		} | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"DT")) | ||||
| 	    { | ||||
| 	    dt=hex2bin_m(value,&i); | ||||
| 	    if (i != 16) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid DT length\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"V")) | ||||
| 	    { | ||||
| 	    v=hex2bin_m(value,&i); | ||||
| 	    if (i != 16) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid V length\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 
 | ||||
| 	    if (!key || !dt) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Missing key or DT\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 
 | ||||
| 	    FIPS_rand_set_key(key, keylen); | ||||
| 	    FIPS_rand_seed(v,16); | ||||
| 	    FIPS_rand_set_dt(dt); | ||||
| 	    if (FIPS_rand_bytes(ret,16) <= 0) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Error getting PRNG value\n"); | ||||
| 	        return; | ||||
| 	        } | ||||
| 
 | ||||
| 	    pv("R",ret,16); | ||||
| 	    OPENSSL_free(key); | ||||
| 	    key = NULL; | ||||
| 	    OPENSSL_free(dt); | ||||
| 	    dt = NULL; | ||||
| 	    OPENSSL_free(v); | ||||
| 	    v = NULL; | ||||
| 	    } | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| static void mct() | ||||
|     { | ||||
|     unsigned char *key = NULL; | ||||
|     unsigned char *v = NULL; | ||||
|     unsigned char *dt = NULL; | ||||
|     unsigned char ret[16]; | ||||
|     char buf[1024]; | ||||
|     char lbuf[1024]; | ||||
|     char *keyword, *value; | ||||
|     long i, keylen; | ||||
|     int j; | ||||
| 
 | ||||
|     keylen = 0; | ||||
| 
 | ||||
|     while(fgets(buf,sizeof buf,stdin) != NULL) | ||||
| 	{ | ||||
| 	fputs(buf,stdout); | ||||
| 	if(!strncmp(buf,"[AES 128-Key]", 13)) | ||||
| 		keylen = 16; | ||||
| 	else if(!strncmp(buf,"[AES 192-Key]", 13)) | ||||
| 		keylen = 24; | ||||
| 	else if(!strncmp(buf,"[AES 256-Key]", 13)) | ||||
| 		keylen = 32; | ||||
| 	if (!parse_line(&keyword, &value, lbuf, buf)) | ||||
| 		continue; | ||||
| 	if(!strcmp(keyword,"Key")) | ||||
| 	    { | ||||
| 	    key=hex2bin_m(value,&i); | ||||
| 	    if (i != keylen) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid key length, expecting %ld\n", keylen); | ||||
| 		return; | ||||
| 		} | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"DT")) | ||||
| 	    { | ||||
| 	    dt=hex2bin_m(value,&i); | ||||
| 	    if (i != 16) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid DT length\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 	    } | ||||
| 	else if(!strcmp(keyword,"V")) | ||||
| 	    { | ||||
| 	    v=hex2bin_m(value,&i); | ||||
| 	    if (i != 16) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Invalid V length\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 
 | ||||
| 	    if (!key || !dt) | ||||
| 		{ | ||||
| 		fprintf(stderr, "Missing key or DT\n"); | ||||
| 		return; | ||||
| 		} | ||||
| 
 | ||||
| 	    FIPS_rand_set_key(key, keylen); | ||||
| 	    FIPS_rand_seed(v,16); | ||||
| 	    for (i = 0; i < 10000; i++) | ||||
| 		{ | ||||
| 		    FIPS_rand_set_dt(dt); | ||||
| 		    if (FIPS_rand_bytes(ret,16) <= 0) | ||||
| 			{ | ||||
| 			fprintf(stderr, "Error getting PRNG value\n"); | ||||
| 		        return; | ||||
| 		        } | ||||
| 		    /* Increment DT */ | ||||
| 		    for (j = 15; j >= 0; j--) | ||||
| 			{ | ||||
| 			dt[j]++; | ||||
| 			if (dt[j]) | ||||
| 				break; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 	    pv("R",ret,16); | ||||
| 	    OPENSSL_free(key); | ||||
| 	    key = NULL; | ||||
| 	    OPENSSL_free(dt); | ||||
| 	    dt = NULL; | ||||
| 	    OPENSSL_free(v); | ||||
| 	    v = NULL; | ||||
| 	    } | ||||
| 	} | ||||
|     } | ||||
| 
 | ||||
| int main(int argc,char **argv) | ||||
|     { | ||||
|     if(argc != 2) | ||||
| 	{ | ||||
| 	fprintf(stderr,"%s [mct|vst]\n",argv[0]); | ||||
| 	exit(1); | ||||
| 	} | ||||
|     fips_set_error_print(); | ||||
|     if(!FIPS_mode_set(1)) | ||||
| 	exit(1); | ||||
|     FIPS_rand_reset(); | ||||
|     if (!FIPS_rand_test_mode()) | ||||
| 	{ | ||||
| 	fprintf(stderr, "Error setting PRNG test mode\n"); | ||||
| 	exit(1); | ||||
| 	} | ||||
|     if(!strcmp(argv[1],"mct")) | ||||
| 	mct(); | ||||
|     else if(!strcmp(argv[1],"vst")) | ||||
| 	vst(); | ||||
|     else | ||||
| 	{ | ||||
| 	fprintf(stderr,"Don't know how to %s.\n",argv[1]); | ||||
| 	exit(1); | ||||
| 	} | ||||
| 
 | ||||
|     return 0; | ||||
|     } | ||||
| #endif | ||||
|  | @ -0,0 +1,101 @@ | |||
| /* fips_rsa_sign.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2007. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/err.h> | ||||
| 
 | ||||
| /* Minimal FIPS versions of FIPS_rsa_new() and FIPS_rsa_free: to
 | ||||
|  * reduce external dependencies.  | ||||
|  */ | ||||
| 
 | ||||
| RSA *FIPS_rsa_new(void) | ||||
| 	{ | ||||
| 	RSA *ret; | ||||
| 	ret = OPENSSL_malloc(sizeof(RSA)); | ||||
| 	if (!ret) | ||||
| 		return NULL; | ||||
| 	memset(ret, 0, sizeof(RSA)); | ||||
| 	ret->meth = RSA_PKCS1_SSLeay(); | ||||
| 	if (ret->meth->init) | ||||
| 		ret->meth->init(ret); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_rsa_free(RSA *r) | ||||
| 	{ | ||||
| 	if (!r) | ||||
| 		return; | ||||
| 	if (r->meth->finish) | ||||
| 		r->meth->finish(r); | ||||
| 	if (r->n != NULL) BN_clear_free(r->n); | ||||
| 	if (r->e != NULL) BN_clear_free(r->e); | ||||
| 	if (r->d != NULL) BN_clear_free(r->d); | ||||
| 	if (r->p != NULL) BN_clear_free(r->p); | ||||
| 	if (r->q != NULL) BN_clear_free(r->q); | ||||
| 	if (r->dmp1 != NULL) BN_clear_free(r->dmp1); | ||||
| 	if (r->dmq1 != NULL) BN_clear_free(r->dmq1); | ||||
| 	if (r->iqmp != NULL) BN_clear_free(r->iqmp); | ||||
| 	if (r->blinding != NULL) BN_BLINDING_free(r->blinding); | ||||
| 	if (r->mt_blinding != NULL) BN_BLINDING_free(r->mt_blinding); | ||||
| 	if (r->bignum_data != NULL) OPENSSL_free_locked(r->bignum_data); | ||||
| 	OPENSSL_free(r); | ||||
| 	} | ||||
| 
 | ||||
|  | @ -0,0 +1,434 @@ | |||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2003-2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPS_EVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/opensslconf.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| static unsigned char n[] = | ||||
| "\x00\xBB\xF8\x2F\x09\x06\x82\xCE\x9C\x23\x38\xAC\x2B\x9D\xA8\x71" | ||||
| "\xF7\x36\x8D\x07\xEE\xD4\x10\x43\xA4\x40\xD6\xB6\xF0\x74\x54\xF5" | ||||
| "\x1F\xB8\xDF\xBA\xAF\x03\x5C\x02\xAB\x61\xEA\x48\xCE\xEB\x6F\xCD" | ||||
| "\x48\x76\xED\x52\x0D\x60\xE1\xEC\x46\x19\x71\x9D\x8A\x5B\x8B\x80" | ||||
| "\x7F\xAF\xB8\xE0\xA3\xDF\xC7\x37\x72\x3E\xE6\xB4\xB7\xD9\x3A\x25" | ||||
| "\x84\xEE\x6A\x64\x9D\x06\x09\x53\x74\x88\x34\xB2\x45\x45\x98\x39" | ||||
| "\x4E\xE0\xAA\xB1\x2D\x7B\x61\xA5\x1F\x52\x7A\x9A\x41\xF6\xC1\x68" | ||||
| "\x7F\xE2\x53\x72\x98\xCA\x2A\x8F\x59\x46\xF8\xE5\xFD\x09\x1D\xBD" | ||||
| "\xCB"; | ||||
| 
 | ||||
| 
 | ||||
| static int setrsakey(RSA *key) | ||||
|     { | ||||
|     static const unsigned char e[] = "\x11"; | ||||
| 
 | ||||
|     static const unsigned char d[] = | ||||
| "\x00\xA5\xDA\xFC\x53\x41\xFA\xF2\x89\xC4\xB9\x88\xDB\x30\xC1\xCD" | ||||
| "\xF8\x3F\x31\x25\x1E\x06\x68\xB4\x27\x84\x81\x38\x01\x57\x96\x41" | ||||
| "\xB2\x94\x10\xB3\xC7\x99\x8D\x6B\xC4\x65\x74\x5E\x5C\x39\x26\x69" | ||||
| "\xD6\x87\x0D\xA2\xC0\x82\xA9\x39\xE3\x7F\xDC\xB8\x2E\xC9\x3E\xDA" | ||||
| "\xC9\x7F\xF3\xAD\x59\x50\xAC\xCF\xBC\x11\x1C\x76\xF1\xA9\x52\x94" | ||||
| "\x44\xE5\x6A\xAF\x68\xC5\x6C\x09\x2C\xD3\x8D\xC3\xBE\xF5\xD2\x0A" | ||||
| "\x93\x99\x26\xED\x4F\x74\xA1\x3E\xDD\xFB\xE1\xA1\xCE\xCC\x48\x94" | ||||
| "\xAF\x94\x28\xC2\xB7\xB8\x88\x3F\xE4\x46\x3A\x4B\xC8\x5B\x1C\xB3" | ||||
| "\xC1"; | ||||
| 
 | ||||
|     static const unsigned char p[] = | ||||
| "\x00\xEE\xCF\xAE\x81\xB1\xB9\xB3\xC9\x08\x81\x0B\x10\xA1\xB5\x60" | ||||
| "\x01\x99\xEB\x9F\x44\xAE\xF4\xFD\xA4\x93\xB8\x1A\x9E\x3D\x84\xF6" | ||||
| "\x32\x12\x4E\xF0\x23\x6E\x5D\x1E\x3B\x7E\x28\xFA\xE7\xAA\x04\x0A" | ||||
| "\x2D\x5B\x25\x21\x76\x45\x9D\x1F\x39\x75\x41\xBA\x2A\x58\xFB\x65" | ||||
| "\x99"; | ||||
| 
 | ||||
|     static const unsigned char q[] = | ||||
| "\x00\xC9\x7F\xB1\xF0\x27\xF4\x53\xF6\x34\x12\x33\xEA\xAA\xD1\xD9" | ||||
| "\x35\x3F\x6C\x42\xD0\x88\x66\xB1\xD0\x5A\x0F\x20\x35\x02\x8B\x9D" | ||||
| "\x86\x98\x40\xB4\x16\x66\xB4\x2E\x92\xEA\x0D\xA3\xB4\x32\x04\xB5" | ||||
| "\xCF\xCE\x33\x52\x52\x4D\x04\x16\xA5\xA4\x41\xE7\x00\xAF\x46\x15" | ||||
| "\x03"; | ||||
| 
 | ||||
|     static const unsigned char dmp1[] = | ||||
| "\x54\x49\x4C\xA6\x3E\xBA\x03\x37\xE4\xE2\x40\x23\xFC\xD6\x9A\x5A" | ||||
| "\xEB\x07\xDD\xDC\x01\x83\xA4\xD0\xAC\x9B\x54\xB0\x51\xF2\xB1\x3E" | ||||
| "\xD9\x49\x09\x75\xEA\xB7\x74\x14\xFF\x59\xC1\xF7\x69\x2E\x9A\x2E" | ||||
| "\x20\x2B\x38\xFC\x91\x0A\x47\x41\x74\xAD\xC9\x3C\x1F\x67\xC9\x81"; | ||||
| 
 | ||||
|     static const unsigned char dmq1[] = | ||||
| "\x47\x1E\x02\x90\xFF\x0A\xF0\x75\x03\x51\xB7\xF8\x78\x86\x4C\xA9" | ||||
| "\x61\xAD\xBD\x3A\x8A\x7E\x99\x1C\x5C\x05\x56\xA9\x4C\x31\x46\xA7" | ||||
| "\xF9\x80\x3F\x8F\x6F\x8A\xE3\x42\xE9\x31\xFD\x8A\xE4\x7A\x22\x0D" | ||||
| "\x1B\x99\xA4\x95\x84\x98\x07\xFE\x39\xF9\x24\x5A\x98\x36\xDA\x3D"; | ||||
|      | ||||
|     static const unsigned char iqmp[] = | ||||
| "\x00\xB0\x6C\x4F\xDA\xBB\x63\x01\x19\x8D\x26\x5B\xDB\xAE\x94\x23" | ||||
| "\xB3\x80\xF2\x71\xF7\x34\x53\x88\x50\x93\x07\x7F\xCD\x39\xE2\x11" | ||||
| "\x9F\xC9\x86\x32\x15\x4F\x58\x83\xB1\x67\xA9\x67\xBF\x40\x2B\x4E" | ||||
| "\x9E\x2E\x0F\x96\x56\xE6\x98\xEA\x36\x66\xED\xFB\x25\x79\x80\x39" | ||||
| "\xF7"; | ||||
| 
 | ||||
|     key->n = BN_bin2bn(n, sizeof(n)-1, key->n); | ||||
|     key->e = BN_bin2bn(e, sizeof(e)-1, key->e); | ||||
|     key->d = BN_bin2bn(d, sizeof(d)-1, key->d); | ||||
|     key->p = BN_bin2bn(p, sizeof(p)-1, key->p); | ||||
|     key->q = BN_bin2bn(q, sizeof(q)-1, key->q); | ||||
|     key->dmp1 = BN_bin2bn(dmp1, sizeof(dmp1)-1, key->dmp1); | ||||
|     key->dmq1 = BN_bin2bn(dmq1, sizeof(dmq1)-1, key->dmq1); | ||||
|     key->iqmp = BN_bin2bn(iqmp, sizeof(iqmp)-1, key->iqmp); | ||||
|     return 1; | ||||
|     } | ||||
| 
 | ||||
| void FIPS_corrupt_rsa() | ||||
|     { | ||||
|     n[0]++; | ||||
|     } | ||||
| 
 | ||||
| /* Known Answer Test (KAT) data for the above RSA private key signing
 | ||||
|  * kat_tbs. | ||||
|  */ | ||||
| 
 | ||||
| static const unsigned char kat_tbs[] = "OpenSSL FIPS 140-2 Public Key RSA KAT"; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_PSS_SHA1[] = { | ||||
|   0x2D, 0xAF, 0x6E, 0xC2, 0x98, 0xFB, 0x8A, 0xA1, 0xB9, 0x46, 0xDA, 0x0F, | ||||
|   0x01, 0x1E, 0x37, 0x93, 0xC2, 0x55, 0x27, 0xE4, 0x1D, 0xD2, 0x90, 0xBB, | ||||
|   0xF4, 0xBF, 0x4A, 0x74, 0x39, 0x51, 0xBB, 0xE8, 0x0C, 0xB7, 0xF8, 0xD3, | ||||
|   0xD1, 0xDF, 0xE7, 0xBE, 0x80, 0x05, 0xC3, 0xB5, 0xC7, 0x83, 0xD5, 0x4C, | ||||
|   0x7F, 0x49, 0xFB, 0x3F, 0x29, 0x9B, 0xE1, 0x12, 0x51, 0x60, 0xD0, 0xA7, | ||||
|   0x0D, 0xA9, 0x28, 0x56, 0x73, 0xD9, 0x07, 0xE3, 0x5E, 0x3F, 0x9B, 0xF5, | ||||
|   0xB6, 0xF3, 0xF2, 0x5E, 0x74, 0xC9, 0x83, 0x81, 0x47, 0xF0, 0xC5, 0x45, | ||||
|   0x0A, 0xE9, 0x8E, 0x38, 0xD7, 0x18, 0xC6, 0x2A, 0x0F, 0xF8, 0xB7, 0x31, | ||||
|   0xD6, 0x55, 0xE4, 0x66, 0x78, 0x81, 0xD4, 0xE6, 0xDB, 0x9F, 0xBA, 0xE8, | ||||
|   0x23, 0xB5, 0x7F, 0xDC, 0x08, 0xEA, 0xD5, 0x26, 0x1E, 0x20, 0x25, 0x84, | ||||
|   0x26, 0xC6, 0x79, 0xC9, 0x9B, 0x3D, 0x7E, 0xA9 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_PSS_SHA224[] = { | ||||
|   0x39, 0x4A, 0x6A, 0x20, 0xBC, 0xE9, 0x33, 0xED, 0xEF, 0xC5, 0x58, 0xA7, | ||||
|   0xFE, 0x81, 0xC4, 0x36, 0x50, 0x9A, 0x2C, 0x82, 0x98, 0x08, 0x95, 0xFA, | ||||
|   0xB1, 0x9E, 0xD2, 0x55, 0x61, 0x87, 0x21, 0x59, 0x87, 0x7B, 0x1F, 0x57, | ||||
|   0x30, 0x9D, 0x0D, 0x4A, 0x06, 0xEB, 0x52, 0x37, 0x55, 0x54, 0x1C, 0x89, | ||||
|   0x83, 0x75, 0x59, 0x65, 0x64, 0x90, 0x2E, 0x16, 0xCC, 0x86, 0x05, 0xEE, | ||||
|   0xB1, 0xE6, 0x7B, 0xBA, 0x16, 0x75, 0x0D, 0x0C, 0x64, 0x0B, 0xAB, 0x22, | ||||
|   0x15, 0x78, 0x6B, 0x6F, 0xA4, 0xFB, 0x77, 0x40, 0x64, 0x62, 0xD1, 0xB5, | ||||
|   0x37, 0x1E, 0xE0, 0x3D, 0xA8, 0xF9, 0xD2, 0xBD, 0xAA, 0x38, 0x24, 0x49, | ||||
|   0x58, 0xD2, 0x74, 0x85, 0xF4, 0xB5, 0x93, 0x8E, 0xF5, 0x03, 0xEA, 0x2D, | ||||
|   0xC8, 0x52, 0xFA, 0xCF, 0x7E, 0x35, 0xB0, 0x6A, 0xAF, 0x95, 0xC0, 0x00, | ||||
|   0x54, 0x76, 0x3D, 0x0C, 0x9C, 0xB2, 0xEE, 0xC0 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_PSS_SHA256[] = { | ||||
|   0x6D, 0x3D, 0xBE, 0x8F, 0x60, 0x6D, 0x25, 0x14, 0xF0, 0x31, 0xE3, 0x89, | ||||
|   0x00, 0x97, 0xFA, 0x99, 0x71, 0x28, 0xE5, 0x10, 0x25, 0x9A, 0xF3, 0x8F, | ||||
|   0x7B, 0xC5, 0xA8, 0x4A, 0x74, 0x51, 0x36, 0xE2, 0x8D, 0x7D, 0x73, 0x28, | ||||
|   0xC1, 0x77, 0xC6, 0x27, 0x97, 0x00, 0x8B, 0x00, 0xA3, 0x96, 0x73, 0x4E, | ||||
|   0x7D, 0x2E, 0x2C, 0x34, 0x68, 0x8C, 0x8E, 0xDF, 0x9D, 0x49, 0x47, 0x05, | ||||
|   0xAB, 0xF5, 0x01, 0xD6, 0x81, 0x47, 0x70, 0xF5, 0x1D, 0x6D, 0x26, 0xBA, | ||||
|   0x2F, 0x7A, 0x54, 0x53, 0x4E, 0xED, 0x71, 0xD9, 0x5A, 0xF3, 0xDA, 0xB6, | ||||
|   0x0B, 0x47, 0x34, 0xAF, 0x90, 0xDC, 0xC8, 0xD9, 0x6F, 0x56, 0xCD, 0x9F, | ||||
|   0x21, 0xB7, 0x7E, 0xAD, 0x7C, 0x2F, 0x75, 0x50, 0x47, 0x12, 0xE4, 0x6D, | ||||
|   0x5F, 0xB7, 0x01, 0xDF, 0xC3, 0x11, 0x6C, 0xA9, 0x9E, 0x49, 0xB9, 0xF6, | ||||
|   0x72, 0xF4, 0xF6, 0xEF, 0x88, 0x1E, 0x2D, 0x1C | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_PSS_SHA384[] = { | ||||
|   0x40, 0xFB, 0xA1, 0x21, 0xF4, 0xB2, 0x40, 0x9A, 0xB4, 0x31, 0xA8, 0xF2, | ||||
|   0xEC, 0x1C, 0xC4, 0xC8, 0x7C, 0x22, 0x65, 0x9C, 0x57, 0x45, 0xCD, 0x5E, | ||||
|   0x86, 0x00, 0xF7, 0x25, 0x78, 0xDE, 0xDC, 0x7A, 0x71, 0x44, 0x9A, 0xCD, | ||||
|   0xAA, 0x25, 0xF4, 0xB2, 0xFC, 0xF0, 0x75, 0xD9, 0x2F, 0x78, 0x23, 0x7F, | ||||
|   0x6F, 0x02, 0xEF, 0xC1, 0xAF, 0xA6, 0x28, 0x16, 0x31, 0xDC, 0x42, 0x6C, | ||||
|   0xB2, 0x44, 0xE5, 0x4D, 0x66, 0xA2, 0xE6, 0x71, 0xF3, 0xAC, 0x4F, 0xFB, | ||||
|   0x91, 0xCA, 0xF5, 0x70, 0xEF, 0x6B, 0x9D, 0xA4, 0xEF, 0xD9, 0x3D, 0x2F, | ||||
|   0x3A, 0xBE, 0x89, 0x38, 0x59, 0x01, 0xBA, 0xDA, 0x32, 0xAD, 0x42, 0x89, | ||||
|   0x98, 0x8B, 0x39, 0x44, 0xF0, 0xFC, 0x38, 0xAC, 0x87, 0x1F, 0xCA, 0x6F, | ||||
|   0x48, 0xF6, 0xAE, 0xD7, 0x45, 0xEE, 0xAE, 0x88, 0x0E, 0x60, 0xF4, 0x55, | ||||
|   0x48, 0x44, 0xEE, 0x1F, 0x90, 0x18, 0x4B, 0xF1 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_PSS_SHA512[] = { | ||||
|   0x07, 0x1E, 0xD8, 0xD5, 0x05, 0xE8, 0xE6, 0xE6, 0x57, 0xAE, 0x63, 0x8C, | ||||
|   0xC6, 0x83, 0xB7, 0xA0, 0x59, 0xBB, 0xF2, 0xC6, 0x8F, 0x12, 0x53, 0x9A, | ||||
|   0x9B, 0x54, 0x9E, 0xB3, 0xC1, 0x1D, 0x23, 0x4D, 0x51, 0xED, 0x9E, 0xDD, | ||||
|   0x4B, 0xF3, 0x46, 0x9B, 0x6B, 0xF6, 0x7C, 0x24, 0x60, 0x79, 0x23, 0x39, | ||||
|   0x01, 0x1C, 0x51, 0xCB, 0xD8, 0xE9, 0x9A, 0x01, 0x67, 0x5F, 0xFE, 0xD7, | ||||
|   0x7C, 0xE3, 0x7F, 0xED, 0xDB, 0x87, 0xBB, 0xF0, 0x3D, 0x78, 0x55, 0x61, | ||||
|   0x57, 0xE3, 0x0F, 0xE3, 0xD2, 0x9D, 0x0C, 0x2A, 0x20, 0xB0, 0x85, 0x13, | ||||
|   0xC5, 0x47, 0x34, 0x0D, 0x32, 0x15, 0xC8, 0xAE, 0x9A, 0x6A, 0x39, 0x63, | ||||
|   0x2D, 0x60, 0xF5, 0x4C, 0xDF, 0x8A, 0x48, 0x4B, 0xBF, 0xF4, 0xA8, 0xFE, | ||||
|   0x76, 0xF2, 0x32, 0x1B, 0x9C, 0x7C, 0xCA, 0xFE, 0x7F, 0x80, 0xC2, 0x88, | ||||
|   0x5C, 0x97, 0x70, 0xB4, 0x26, 0xC9, 0x14, 0x8B | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_SHA1[] = { | ||||
|   0x71, 0xEE, 0x1A, 0xC0, 0xFE, 0x01, 0x93, 0x54, 0x79, 0x5C, 0xF2, 0x4C, | ||||
|   0x4A, 0xFD, 0x1A, 0x05, 0x8F, 0x64, 0xB1, 0x6D, 0x61, 0x33, 0x8D, 0x9B, | ||||
|   0xE7, 0xFD, 0x60, 0xA3, 0x83, 0xB5, 0xA3, 0x51, 0x55, 0x77, 0x90, 0xCF, | ||||
|   0xDC, 0x22, 0x37, 0x8E, 0xD0, 0xE1, 0xAE, 0x09, 0xE3, 0x3D, 0x1E, 0xF8, | ||||
|   0x80, 0xD1, 0x8B, 0xC2, 0xEC, 0x0A, 0xD7, 0x6B, 0x88, 0x8B, 0x8B, 0xA1, | ||||
|   0x20, 0x22, 0xBE, 0x59, 0x5B, 0xE0, 0x23, 0x24, 0xA1, 0x49, 0x30, 0xBA, | ||||
|   0xA9, 0x9E, 0xE8, 0xB1, 0x8A, 0x62, 0x16, 0xBF, 0x4E, 0xCA, 0x2E, 0x4E, | ||||
|   0xBC, 0x29, 0xA8, 0x67, 0x13, 0xB7, 0x9F, 0x1D, 0x04, 0x44, 0xE5, 0x5F, | ||||
|   0x35, 0x07, 0x11, 0xBC, 0xED, 0x19, 0x37, 0x21, 0xCF, 0x23, 0x48, 0x1F, | ||||
|   0x72, 0x05, 0xDE, 0xE6, 0xE8, 0x7F, 0x33, 0x8A, 0x76, 0x4B, 0x2F, 0x95, | ||||
|   0xDF, 0xF1, 0x5F, 0x84, 0x80, 0xD9, 0x46, 0xB4 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_SHA224[] = { | ||||
|   0x62, 0xAA, 0x79, 0xA9, 0x18, 0x0E, 0x5F, 0x8C, 0xBB, 0xB7, 0x15, 0xF9, | ||||
|   0x25, 0xBB, 0xFA, 0xD4, 0x3A, 0x34, 0xED, 0x9E, 0xA0, 0xA9, 0x18, 0x8D, | ||||
|   0x5B, 0x55, 0x9A, 0x7E, 0x1E, 0x08, 0x08, 0x60, 0xC5, 0x1A, 0xC5, 0x89, | ||||
|   0x08, 0xE2, 0x1B, 0xBD, 0x62, 0x50, 0x17, 0x76, 0x30, 0x2C, 0x9E, 0xCD, | ||||
|   0xA4, 0x02, 0xAD, 0xB1, 0x6D, 0x44, 0x6D, 0xD5, 0xC6, 0x45, 0x41, 0xE5, | ||||
|   0xEE, 0x1F, 0x8D, 0x7E, 0x08, 0x16, 0xA6, 0xE1, 0x5E, 0x0B, 0xA9, 0xCC, | ||||
|   0xDB, 0x59, 0x55, 0x87, 0x09, 0x25, 0x70, 0x86, 0x84, 0x02, 0xC6, 0x3B, | ||||
|   0x0B, 0x44, 0x4C, 0x46, 0x95, 0xF4, 0xF8, 0x5A, 0x91, 0x28, 0x3E, 0xB2, | ||||
|   0x58, 0x2E, 0x06, 0x45, 0x49, 0xE0, 0x92, 0xE2, 0xC0, 0x66, 0xE6, 0x35, | ||||
|   0xD9, 0x79, 0x7F, 0x17, 0x5E, 0x02, 0x73, 0x04, 0x77, 0x82, 0xE6, 0xDC, | ||||
|   0x40, 0x21, 0x89, 0x8B, 0x37, 0x3E, 0x1E, 0x8D | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_SHA256[] = { | ||||
|   0x0D, 0x55, 0xE2, 0xAA, 0x81, 0xDB, 0x8E, 0x82, 0x05, 0x17, 0xA5, 0x23, | ||||
|   0xE7, 0x3B, 0x1D, 0xAF, 0xFB, 0x8C, 0xD0, 0x81, 0x20, 0x7B, 0xAA, 0x23, | ||||
|   0x92, 0x87, 0x8C, 0xD1, 0x53, 0x85, 0x16, 0xDC, 0xBE, 0xAD, 0x6F, 0x35, | ||||
|   0x98, 0x2D, 0x69, 0x84, 0xBF, 0xD9, 0x8A, 0x01, 0x17, 0x58, 0xB2, 0x6E, | ||||
|   0x2C, 0x44, 0x9B, 0x90, 0xF1, 0xFB, 0x51, 0xE8, 0x6A, 0x90, 0x2D, 0x18, | ||||
|   0x0E, 0xC0, 0x90, 0x10, 0x24, 0xA9, 0x1D, 0xB3, 0x58, 0x7A, 0x91, 0x30, | ||||
|   0xBE, 0x22, 0xC7, 0xD3, 0xEC, 0xC3, 0x09, 0x5D, 0xBF, 0xE2, 0x80, 0x3A, | ||||
|   0x7C, 0x85, 0xB4, 0xBC, 0xD1, 0xE9, 0xF0, 0x5C, 0xDE, 0x81, 0xA6, 0x38, | ||||
|   0xB8, 0x42, 0xBB, 0x86, 0xC5, 0x9D, 0xCE, 0x7C, 0x2C, 0xEE, 0xD1, 0xDA, | ||||
|   0x27, 0x48, 0x2B, 0xF5, 0xAB, 0xB9, 0xF7, 0x80, 0xD1, 0x90, 0x27, 0x90, | ||||
|   0xBD, 0x44, 0x97, 0x60, 0xCD, 0x57, 0xC0, 0x7A | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_SHA384[] = { | ||||
|   0x1D, 0xE3, 0x6A, 0xDD, 0x27, 0x4C, 0xC0, 0xA5, 0x27, 0xEF, 0xE6, 0x1F, | ||||
|   0xD2, 0x91, 0x68, 0x59, 0x04, 0xAE, 0xBD, 0x99, 0x63, 0x56, 0x47, 0xC7, | ||||
|   0x6F, 0x22, 0x16, 0x48, 0xD0, 0xF9, 0x18, 0xA9, 0xCA, 0xFA, 0x5D, 0x5C, | ||||
|   0xA7, 0x65, 0x52, 0x8A, 0xC8, 0x44, 0x7E, 0x86, 0x5D, 0xA9, 0xA6, 0x55, | ||||
|   0x65, 0x3E, 0xD9, 0x2D, 0x02, 0x38, 0xA8, 0x79, 0x28, 0x7F, 0xB6, 0xCF, | ||||
|   0x82, 0xDD, 0x7E, 0x55, 0xE1, 0xB1, 0xBC, 0xE2, 0x19, 0x2B, 0x30, 0xC2, | ||||
|   0x1B, 0x2B, 0xB0, 0x82, 0x46, 0xAC, 0x4B, 0xD1, 0xE2, 0x7D, 0xEB, 0x8C, | ||||
|   0xFF, 0x95, 0xE9, 0x6A, 0x1C, 0x3D, 0x4D, 0xBF, 0x8F, 0x8B, 0x9C, 0xCD, | ||||
|   0xEA, 0x85, 0xEE, 0x00, 0xDC, 0x1C, 0xA7, 0xEB, 0xD0, 0x8F, 0x99, 0xF1, | ||||
|   0x16, 0x28, 0x24, 0x64, 0x04, 0x39, 0x2D, 0x58, 0x1E, 0x37, 0xDC, 0x04, | ||||
|   0xBD, 0x31, 0xA2, 0x2F, 0xB3, 0x35, 0x56, 0xBF | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_SHA512[] = { | ||||
|   0x69, 0x52, 0x1B, 0x51, 0x5E, 0x06, 0xCA, 0x9B, 0x16, 0x51, 0x5D, 0xCF, | ||||
|   0x49, 0x25, 0x4A, 0xA1, 0x6A, 0x77, 0x4C, 0x36, 0x40, 0xF8, 0xB2, 0x9A, | ||||
|   0x15, 0xEA, 0x5C, 0xE5, 0xE6, 0x82, 0xE0, 0x86, 0x82, 0x6B, 0x32, 0xF1, | ||||
|   0x04, 0xC1, 0x5A, 0x1A, 0xED, 0x1E, 0x9A, 0xB6, 0x4C, 0x54, 0x9F, 0xD8, | ||||
|   0x8D, 0xCC, 0xAC, 0x8A, 0xBB, 0x9C, 0x82, 0x3F, 0xA6, 0x53, 0x62, 0xB5, | ||||
|   0x80, 0xE2, 0xBC, 0xDD, 0x67, 0x2B, 0xD9, 0x3F, 0xE4, 0x75, 0x92, 0x6B, | ||||
|   0xAF, 0x62, 0x7C, 0x52, 0xF0, 0xEE, 0x33, 0xDF, 0x1B, 0x1D, 0x47, 0xE6, | ||||
|   0x59, 0x56, 0xA5, 0xB9, 0x5C, 0xE6, 0x77, 0x78, 0x16, 0x63, 0x84, 0x05, | ||||
|   0x6F, 0x0E, 0x2B, 0x31, 0x9D, 0xF7, 0x7F, 0xB2, 0x64, 0x71, 0xE0, 0x2D, | ||||
|   0x3E, 0x62, 0xCE, 0xB5, 0x3F, 0x88, 0xDF, 0x2D, 0xAB, 0x98, 0x65, 0x91, | ||||
|   0xDF, 0x70, 0x14, 0xA5, 0x3F, 0x36, 0xAB, 0x84 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_X931_SHA1[] = { | ||||
|   0x86, 0xB4, 0x18, 0xBA, 0xD1, 0x80, 0xB6, 0x7C, 0x42, 0x45, 0x4D, 0xDF, | ||||
|   0xE9, 0x2D, 0xE1, 0x83, 0x5F, 0xB5, 0x2F, 0xC9, 0xCD, 0xC4, 0xB2, 0x75, | ||||
|   0x80, 0xA4, 0xF1, 0x4A, 0xE7, 0x83, 0x12, 0x1E, 0x1E, 0x14, 0xB8, 0xAC, | ||||
|   0x35, 0xE2, 0xAA, 0x0B, 0x5C, 0xF8, 0x38, 0x4D, 0x04, 0xEE, 0xA9, 0x97, | ||||
|   0x70, 0xFB, 0x5E, 0xE7, 0xB7, 0xE3, 0x62, 0x23, 0x4B, 0x38, 0xBE, 0xD6, | ||||
|   0x53, 0x15, 0xF7, 0xDF, 0x87, 0xB4, 0x0E, 0xCC, 0xB1, 0x1A, 0x11, 0x19, | ||||
|   0xEE, 0x51, 0xCC, 0x92, 0xDD, 0xBC, 0x63, 0x29, 0x63, 0x0C, 0x59, 0xD7, | ||||
|   0x6F, 0x4C, 0x3C, 0x37, 0x5B, 0x37, 0x03, 0x61, 0x7D, 0x24, 0x1C, 0x99, | ||||
|   0x48, 0xAF, 0x82, 0xFE, 0x32, 0x41, 0x9B, 0xB2, 0xDB, 0xEA, 0xED, 0x76, | ||||
|   0x8E, 0x6E, 0xCA, 0x7E, 0x4E, 0x14, 0xBA, 0x30, 0x84, 0x1C, 0xB3, 0x67, | ||||
|   0xA3, 0x29, 0x80, 0x70, 0x54, 0x68, 0x7D, 0x49 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_X931_SHA256[] = { | ||||
|   0x7E, 0xA2, 0x77, 0xFE, 0xB8, 0x54, 0x8A, 0xC7, 0x7F, 0x64, 0x54, 0x89, | ||||
|   0xE5, 0x52, 0x15, 0x8E, 0x52, 0x96, 0x4E, 0xA6, 0x58, 0x92, 0x1C, 0xDD, | ||||
|   0xEA, 0xA2, 0x2D, 0x5C, 0xD1, 0x62, 0x00, 0x49, 0x05, 0x95, 0x73, 0xCF, | ||||
|   0x16, 0x76, 0x68, 0xF6, 0xC6, 0x5E, 0x80, 0xB8, 0xB8, 0x7B, 0xC8, 0x9B, | ||||
|   0xC6, 0x53, 0x88, 0x26, 0x20, 0x88, 0x73, 0xB6, 0x13, 0xB8, 0xF0, 0x4B, | ||||
|   0x00, 0x85, 0xF3, 0xDD, 0x07, 0x50, 0xEB, 0x20, 0xC4, 0x38, 0x0E, 0x98, | ||||
|   0xAD, 0x4E, 0x49, 0x2C, 0xD7, 0x65, 0xA5, 0x19, 0x0E, 0x59, 0x01, 0xEC, | ||||
|   0x7E, 0x75, 0x89, 0x69, 0x2E, 0x63, 0x76, 0x85, 0x46, 0x8D, 0xA0, 0x8C, | ||||
|   0x33, 0x1D, 0x82, 0x8C, 0x03, 0xEA, 0x69, 0x88, 0x35, 0xA1, 0x42, 0xBD, | ||||
|   0x21, 0xED, 0x8D, 0xBC, 0xBC, 0xDB, 0x30, 0xFF, 0x86, 0xF0, 0x5B, 0xDC, | ||||
|   0xE3, 0xE2, 0xE8, 0x0A, 0x0A, 0x29, 0x94, 0x80 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_X931_SHA384[] = { | ||||
|   0x5C, 0x7D, 0x96, 0x35, 0xEC, 0x7E, 0x11, 0x38, 0xBB, 0x7B, 0xEC, 0x7B, | ||||
|   0xF2, 0x82, 0x8E, 0x99, 0xBD, 0xEF, 0xD8, 0xAE, 0xD7, 0x39, 0x37, 0xCB, | ||||
|   0xE6, 0x4F, 0x5E, 0x0A, 0x13, 0xE4, 0x2E, 0x40, 0xB9, 0xBE, 0x2E, 0xE3, | ||||
|   0xEF, 0x78, 0x83, 0x18, 0x44, 0x35, 0x9C, 0x8E, 0xD7, 0x4A, 0x63, 0xF6, | ||||
|   0x57, 0xC2, 0xB0, 0x08, 0x51, 0x73, 0xCF, 0xCA, 0x99, 0x66, 0xEE, 0x31, | ||||
|   0xD8, 0x69, 0xE9, 0xAB, 0x13, 0x27, 0x7B, 0x41, 0x1E, 0x6D, 0x8D, 0xF1, | ||||
|   0x3E, 0x9C, 0x35, 0x95, 0x58, 0xDD, 0x2B, 0xD5, 0xA0, 0x60, 0x41, 0x79, | ||||
|   0x24, 0x22, 0xE4, 0xB7, 0xBF, 0x47, 0x53, 0xF6, 0x34, 0xD5, 0x7C, 0xFF, | ||||
|   0x0E, 0x09, 0xEE, 0x2E, 0xE2, 0x37, 0xB9, 0xDE, 0xC5, 0x12, 0x44, 0x35, | ||||
|   0xEF, 0x01, 0xE6, 0x5E, 0x39, 0x31, 0x2D, 0x71, 0xA5, 0xDC, 0xC6, 0x6D, | ||||
|   0xE2, 0xCD, 0x85, 0xDB, 0x73, 0x82, 0x65, 0x28 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char kat_RSA_X931_SHA512[] = { | ||||
|   0xA6, 0x65, 0xA2, 0x77, 0x4F, 0xB3, 0x86, 0xCB, 0x64, 0x3A, 0xC1, 0x63, | ||||
|   0xFC, 0xA1, 0xAA, 0xCB, 0x9B, 0x79, 0xDD, 0x4B, 0xE1, 0xD9, 0xDA, 0xAC, | ||||
|   0xE7, 0x47, 0x09, 0xB2, 0x11, 0x4B, 0x8A, 0xAA, 0x05, 0x9E, 0x77, 0xD7, | ||||
|   0x3A, 0xBD, 0x5E, 0x53, 0x09, 0x4A, 0xE6, 0x0F, 0x5E, 0xF9, 0x14, 0x28, | ||||
|   0xA0, 0x99, 0x74, 0x64, 0x70, 0x4E, 0xF2, 0xE3, 0xFA, 0xC7, 0xF8, 0xC5, | ||||
|   0x6E, 0x2B, 0x79, 0x96, 0x0D, 0x0C, 0xC8, 0x10, 0x34, 0x53, 0xD2, 0xAF, | ||||
|   0x17, 0x0E, 0xE0, 0xBF, 0x79, 0xF6, 0x04, 0x72, 0x10, 0xE0, 0xF6, 0xD0, | ||||
|   0xCE, 0x8A, 0x6F, 0xA1, 0x95, 0x89, 0xBF, 0x58, 0x8F, 0x46, 0x5F, 0x09, | ||||
|   0x9F, 0x09, 0xCA, 0x84, 0x15, 0x85, 0xE0, 0xED, 0x04, 0x2D, 0xFB, 0x7C, | ||||
|   0x36, 0x35, 0x21, 0x31, 0xC3, 0xFD, 0x92, 0x42, 0x11, 0x30, 0x71, 0x1B, | ||||
|   0x60, 0x83, 0x18, 0x88, 0xA3, 0xF5, 0x59, 0xC3 | ||||
| }; | ||||
| 
 | ||||
| 
 | ||||
| int FIPS_selftest_rsa() | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	RSA *key = NULL; | ||||
| 	EVP_PKEY pk; | ||||
| 	key=FIPS_rsa_new(); | ||||
| 	setrsakey(key); | ||||
| 	pk.type = EVP_PKEY_RSA; | ||||
| 	pk.pkey.rsa = key; | ||||
| 
 | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_SHA1, sizeof(kat_RSA_SHA1), | ||||
| 				EVP_sha1(), RSA_PKCS1_PADDING, | ||||
| 				"RSA SHA1 PKCS#1")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_SHA224, sizeof(kat_RSA_SHA224), | ||||
| 				EVP_sha224(), RSA_PKCS1_PADDING, | ||||
| 				"RSA SHA224 PKCS#1")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_SHA256, sizeof(kat_RSA_SHA256), | ||||
| 				EVP_sha256(), RSA_PKCS1_PADDING, | ||||
| 				"RSA SHA256 PKCS#1")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_SHA384, sizeof(kat_RSA_SHA384), | ||||
| 				EVP_sha384(), RSA_PKCS1_PADDING, | ||||
| 				"RSA SHA384 PKCS#1")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_SHA512, sizeof(kat_RSA_SHA512), | ||||
| 				EVP_sha512(), RSA_PKCS1_PADDING, | ||||
| 				"RSA SHA512 PKCS#1")) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_PSS_SHA1, sizeof(kat_RSA_PSS_SHA1), | ||||
| 				EVP_sha1(), RSA_PKCS1_PSS_PADDING, | ||||
| 				"RSA SHA1 PSS")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_PSS_SHA224, sizeof(kat_RSA_PSS_SHA224), | ||||
| 				EVP_sha224(), RSA_PKCS1_PSS_PADDING, | ||||
| 				"RSA SHA224 PSS")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_PSS_SHA256, sizeof(kat_RSA_PSS_SHA256), | ||||
| 				EVP_sha256(), RSA_PKCS1_PSS_PADDING, | ||||
| 				"RSA SHA256 PSS")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_PSS_SHA384, sizeof(kat_RSA_PSS_SHA384), | ||||
| 				EVP_sha384(), RSA_PKCS1_PSS_PADDING, | ||||
| 				"RSA SHA384 PSS")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 				kat_RSA_PSS_SHA512, sizeof(kat_RSA_PSS_SHA512), | ||||
| 				EVP_sha512(), RSA_PKCS1_PSS_PADDING, | ||||
| 				"RSA SHA512 PSS")) | ||||
| 		goto err; | ||||
| 
 | ||||
| 
 | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 			kat_RSA_X931_SHA1, sizeof(kat_RSA_X931_SHA1), | ||||
| 			EVP_sha1(), RSA_X931_PADDING, | ||||
| 			"RSA SHA1 X931")) | ||||
| 		goto err; | ||||
| 	/* NB: SHA224 not supported in X9.31 */ | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 			kat_RSA_X931_SHA256, sizeof(kat_RSA_X931_SHA256), | ||||
| 			EVP_sha256(), RSA_X931_PADDING, | ||||
| 			"RSA SHA256 X931")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 			kat_RSA_X931_SHA384, sizeof(kat_RSA_X931_SHA384), | ||||
| 			EVP_sha384(), RSA_X931_PADDING, | ||||
| 			"RSA SHA384 X931")) | ||||
| 		goto err; | ||||
| 	if (!fips_pkey_signature_test(&pk, kat_tbs, sizeof(kat_tbs) - 1, | ||||
| 			kat_RSA_X931_SHA512, sizeof(kat_RSA_X931_SHA512), | ||||
| 			EVP_sha512(), RSA_X931_PADDING, | ||||
| 			"RSA SHA512 X931")) | ||||
| 		goto err; | ||||
| 
 | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	err: | ||||
| 	FIPS_rsa_free(key); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| #endif /* def OPENSSL_FIPS */ | ||||
|  | @ -0,0 +1,399 @@ | |||
| /* fips_rsa_sign.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2007. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/sha.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| /* FIPS versions of RSA_sign() and RSA_verify().
 | ||||
|  * These will only have to deal with SHA* signatures and by including | ||||
|  * pregenerated encodings all ASN1 dependencies can be avoided | ||||
|  */ | ||||
| 
 | ||||
| /* Standard encodings including NULL parameter */ | ||||
| 
 | ||||
| static const unsigned char sha1_bin[] = { | ||||
|   0x30, 0x21, 0x30, 0x09, 0x06, 0x05, 0x2b, 0x0e, 0x03, 0x02, 0x1a, 0x05, | ||||
|   0x00, 0x04, 0x14 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char sha224_bin[] = { | ||||
|   0x30, 0x2d, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x04, 0x05, 0x00, 0x04, 0x1c | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char sha256_bin[] = { | ||||
|   0x30, 0x31, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x01, 0x05, 0x00, 0x04, 0x20 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char sha384_bin[] = { | ||||
|   0x30, 0x41, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x02, 0x05, 0x00, 0x04, 0x30 | ||||
| }; | ||||
| 
 | ||||
| static const unsigned char sha512_bin[] = { | ||||
|   0x30, 0x51, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x03, 0x05, 0x00, 0x04, 0x40 | ||||
| }; | ||||
| 
 | ||||
| /* Alternate encodings with absent parameters. We don't generate signature
 | ||||
|  * using this format but do tolerate received signatures of this form. | ||||
|  */ | ||||
| 
 | ||||
| static unsigned char sha1_nn_bin[] = { | ||||
|   0x30, 0x1f, 0x30, 0x07, 0x06, 0x05, 0x2b, 0x0e, 0x03, 0x02, 0x1a, 0x04, | ||||
|   0x14 | ||||
| }; | ||||
| 
 | ||||
| static unsigned char sha224_nn_bin[] = { | ||||
|   0x30, 0x2b, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x04, 0x04, 0x1c | ||||
| }; | ||||
| 
 | ||||
| static unsigned char sha256_nn_bin[] = { | ||||
|   0x30, 0x2f, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x01, 0x04, 0x20 | ||||
| }; | ||||
| 
 | ||||
| static unsigned char sha384_nn_bin[] = { | ||||
|   0x30, 0x3f, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x02, 0x04, 0x30 | ||||
| }; | ||||
| 
 | ||||
| static unsigned char sha512_nn_bin[] = { | ||||
|   0x30, 0x4f, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, | ||||
|   0x04, 0x02, 0x03, 0x04, 0x40 | ||||
| }; | ||||
| 
 | ||||
| 
 | ||||
| static const unsigned char *fips_digestinfo_encoding(int nid, unsigned int *len) | ||||
| 	{ | ||||
| 	switch (nid) | ||||
| 		{ | ||||
| 
 | ||||
| 		case NID_sha1: | ||||
| 		*len = sizeof(sha1_bin); | ||||
| 		return sha1_bin; | ||||
| 
 | ||||
| 		case NID_sha224: | ||||
| 		*len = sizeof(sha224_bin); | ||||
| 		return sha224_bin; | ||||
| 
 | ||||
| 		case NID_sha256: | ||||
| 		*len = sizeof(sha256_bin); | ||||
| 		return sha256_bin; | ||||
| 
 | ||||
| 		case NID_sha384: | ||||
| 		*len = sizeof(sha384_bin); | ||||
| 		return sha384_bin; | ||||
| 
 | ||||
| 		case NID_sha512: | ||||
| 		*len = sizeof(sha512_bin); | ||||
| 		return sha512_bin; | ||||
| 
 | ||||
| 		default: | ||||
| 		return NULL; | ||||
| 
 | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| static const unsigned char *fips_digestinfo_nn_encoding(int nid, unsigned int *len) | ||||
| 	{ | ||||
| 	switch (nid) | ||||
| 		{ | ||||
| 
 | ||||
| 		case NID_sha1: | ||||
| 		*len = sizeof(sha1_nn_bin); | ||||
| 		return sha1_nn_bin; | ||||
| 
 | ||||
| 		case NID_sha224: | ||||
| 		*len = sizeof(sha224_nn_bin); | ||||
| 		return sha224_nn_bin; | ||||
| 
 | ||||
| 		case NID_sha256: | ||||
| 		*len = sizeof(sha256_nn_bin); | ||||
| 		return sha256_nn_bin; | ||||
| 
 | ||||
| 		case NID_sha384: | ||||
| 		*len = sizeof(sha384_nn_bin); | ||||
| 		return sha384_nn_bin; | ||||
| 
 | ||||
| 		case NID_sha512: | ||||
| 		*len = sizeof(sha512_nn_bin); | ||||
| 		return sha512_nn_bin; | ||||
| 
 | ||||
| 		default: | ||||
| 		return NULL; | ||||
| 
 | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 
 | ||||
| int FIPS_rsa_sign_ctx(RSA *rsa, EVP_MD_CTX *ctx, | ||||
| 			int rsa_pad_mode, int saltlen, const EVP_MD *mgf1Hash, | ||||
| 			unsigned char *sigret, unsigned int *siglen) | ||||
| 	{ | ||||
| 	int i=0,j,ret=0; | ||||
| 	unsigned int dlen; | ||||
| 	const unsigned char *der; | ||||
| 	unsigned int m_len; | ||||
| 	const EVP_MD *mhash; | ||||
| 	int md_type; | ||||
| 	/* Largest DigestInfo: 19 (max encoding) + max MD */ | ||||
| 	unsigned char tmpdinfo[19 + EVP_MAX_MD_SIZE]; | ||||
| 	unsigned char md[EVP_MAX_MD_SIZE + 1]; | ||||
| 
 | ||||
|         EVP_DigestFinal_ex(ctx, md, &m_len); | ||||
| 
 | ||||
| 	mhash = M_EVP_MD_CTX_md(ctx); | ||||
| 	md_type = M_EVP_MD_type(mhash); | ||||
| 
 | ||||
| 	if (rsa_pad_mode == RSA_X931_PADDING) | ||||
| 		{ | ||||
| 		int hash_id; | ||||
| 		memcpy(tmpdinfo, md, m_len); | ||||
| 		hash_id = RSA_X931_hash_id(md_type); | ||||
| 		if (hash_id == -1) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_SIGN,RSA_R_UNKNOWN_ALGORITHM_TYPE); | ||||
| 			return 0; | ||||
| 			} | ||||
| 		tmpdinfo[m_len] = (unsigned char)hash_id; | ||||
| 		i = m_len + 1; | ||||
| 		} | ||||
| 	else if (rsa_pad_mode == RSA_PKCS1_PADDING) | ||||
| 		{ | ||||
| 
 | ||||
| 		der = fips_digestinfo_encoding(md_type, &dlen); | ||||
| 		 | ||||
| 		if (!der) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_SIGN,RSA_R_UNKNOWN_ALGORITHM_TYPE); | ||||
| 			return 0; | ||||
| 			} | ||||
| 		memcpy(tmpdinfo, der, dlen); | ||||
| 		memcpy(tmpdinfo + dlen, md, m_len); | ||||
| 
 | ||||
| 		i = dlen + m_len; | ||||
| 
 | ||||
| 		} | ||||
| 	else if (rsa_pad_mode == RSA_PKCS1_PSS_PADDING) | ||||
| 		{ | ||||
| 		unsigned char *sbuf; | ||||
| 		i = RSA_size(rsa); | ||||
| 		sbuf = OPENSSL_malloc(RSA_size(rsa)); | ||||
| 		if (!sbuf) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_SIGN,ERR_R_MALLOC_FAILURE); | ||||
| 			goto psserr; | ||||
| 			} | ||||
| 		if (!RSA_padding_add_PKCS1_PSS_mgf1(rsa, sbuf, md, mhash,  | ||||
| 							mgf1Hash, saltlen)) | ||||
| 			goto psserr; | ||||
| 		j=rsa->meth->rsa_priv_enc(i,sbuf,sigret,rsa,RSA_NO_PADDING); | ||||
| 		if (j > 0) | ||||
| 			{ | ||||
| 			ret=1; | ||||
| 			*siglen=j; | ||||
| 			} | ||||
| 		psserr: | ||||
| 		OPENSSL_cleanse(md,m_len); | ||||
| 		OPENSSL_cleanse(sbuf, i); | ||||
| 		OPENSSL_free(sbuf); | ||||
| 		return ret; | ||||
| 		} | ||||
| 
 | ||||
| 	j=RSA_size(rsa); | ||||
| 	if (i > (j-RSA_PKCS1_PADDING_SIZE)) | ||||
| 		{ | ||||
| 		RSAerr(RSA_F_FIPS_RSA_SIGN,RSA_R_DIGEST_TOO_BIG_FOR_RSA_KEY); | ||||
| 		goto done; | ||||
| 		} | ||||
| 	/* NB: call underlying method directly to avoid FIPS blocking */ | ||||
| 	j=rsa->meth->rsa_priv_enc(i,tmpdinfo,sigret,rsa,rsa_pad_mode); | ||||
| 	if (j > 0) | ||||
| 		{ | ||||
| 		ret=1; | ||||
| 		*siglen=j; | ||||
| 		} | ||||
| 
 | ||||
| 	done: | ||||
| 	OPENSSL_cleanse(tmpdinfo,i); | ||||
| 	OPENSSL_cleanse(md,m_len); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_rsa_verify_ctx(RSA *rsa, EVP_MD_CTX *ctx, | ||||
| 			int rsa_pad_mode, int saltlen, const EVP_MD *mgf1Hash, | ||||
| 			unsigned char *sigbuf, unsigned int siglen) | ||||
| 	{ | ||||
| 	int i,ret=0; | ||||
| 	unsigned int dlen, diglen; | ||||
| 	unsigned char *s; | ||||
| 	const unsigned char *der; | ||||
| 	unsigned char dig[EVP_MAX_MD_SIZE]; | ||||
| 	const EVP_MD *mhash; | ||||
| 	int md_type; | ||||
| 	int rsa_dec_pad_mode; | ||||
| 
 | ||||
| 	if (siglen != (unsigned int)RSA_size(rsa)) | ||||
| 		{ | ||||
| 		RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_WRONG_SIGNATURE_LENGTH); | ||||
| 		return(0); | ||||
| 		} | ||||
| 
 | ||||
| 	mhash = M_EVP_MD_CTX_md(ctx); | ||||
| 	md_type = M_EVP_MD_type(mhash); | ||||
| 
 | ||||
|         EVP_DigestFinal_ex(ctx, dig, &diglen); | ||||
| 
 | ||||
| 	s= OPENSSL_malloc((unsigned int)siglen); | ||||
| 	if (s == NULL) | ||||
| 		{ | ||||
| 		RSAerr(RSA_F_FIPS_RSA_VERIFY,ERR_R_MALLOC_FAILURE); | ||||
| 		goto err; | ||||
| 		} | ||||
| 
 | ||||
| 	if (rsa_pad_mode == RSA_PKCS1_PSS_PADDING) | ||||
| 		rsa_dec_pad_mode = RSA_NO_PADDING; | ||||
| 	else | ||||
| 		rsa_dec_pad_mode = rsa_pad_mode; | ||||
| 
 | ||||
| 	/* NB: call underlying method directly to avoid FIPS blocking */ | ||||
| 	i=rsa->meth->rsa_pub_dec((int)siglen,sigbuf,s, rsa, rsa_dec_pad_mode); | ||||
| 
 | ||||
| 	if (i <= 0) goto err; | ||||
| 
 | ||||
| 	if (rsa_pad_mode == RSA_X931_PADDING) | ||||
| 		{ | ||||
| 		int hash_id; | ||||
| 		if (i != (int)(diglen + 1)) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_BAD_SIGNATURE); | ||||
| 			goto err; | ||||
| 			} | ||||
| 		hash_id = RSA_X931_hash_id(md_type); | ||||
| 		if (hash_id == -1) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_UNKNOWN_ALGORITHM_TYPE); | ||||
| 			goto err; | ||||
| 			} | ||||
| 		if (s[diglen] != (unsigned char)hash_id) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_BAD_SIGNATURE); | ||||
| 			goto err; | ||||
| 			} | ||||
| 		if (memcmp(s, dig, diglen)) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_BAD_SIGNATURE); | ||||
| 			goto err; | ||||
| 			} | ||||
| 		ret = 1; | ||||
| 		} | ||||
| 	else if (rsa_pad_mode == RSA_PKCS1_PADDING) | ||||
| 		{ | ||||
| 
 | ||||
| 		der = fips_digestinfo_encoding(md_type, &dlen); | ||||
| 		 | ||||
| 		if (!der) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_UNKNOWN_ALGORITHM_TYPE); | ||||
| 			return(0); | ||||
| 			} | ||||
| 
 | ||||
| 		/* Compare, DigestInfo length, DigestInfo header and finally
 | ||||
| 		 * digest value itself | ||||
| 		 */ | ||||
| 
 | ||||
| 		/* If length mismatch try alternate encoding */ | ||||
| 		if (i != (int)(dlen + diglen)) | ||||
| 			der = fips_digestinfo_nn_encoding(md_type, &dlen); | ||||
| 
 | ||||
| 		if ((i != (int)(dlen + diglen)) || memcmp(der, s, dlen) | ||||
| 			|| memcmp(s + dlen, dig, diglen)) | ||||
| 			{ | ||||
| 			RSAerr(RSA_F_FIPS_RSA_VERIFY,RSA_R_BAD_SIGNATURE); | ||||
| 			goto err; | ||||
| 			} | ||||
| 		ret = 1; | ||||
| 
 | ||||
| 		} | ||||
| 	else if (rsa_pad_mode == RSA_PKCS1_PSS_PADDING) | ||||
| 		{ | ||||
| 		ret = RSA_verify_PKCS1_PSS_mgf1(rsa, dig, mhash, mgf1Hash, | ||||
| 						s, saltlen); | ||||
| 		if (ret < 0) | ||||
| 			ret = 0; | ||||
| 		} | ||||
| err: | ||||
| 	if (s != NULL) | ||||
| 		{ | ||||
| 		OPENSSL_cleanse(s, siglen); | ||||
| 		OPENSSL_free(s); | ||||
| 		} | ||||
| 	return(ret); | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,280 @@ | |||
| /* crypto/rsa/rsa_gen.c */ | ||||
| /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
 | ||||
|  * All rights reserved. | ||||
|  * | ||||
|  * This package is an SSL implementation written | ||||
|  * by Eric Young (eay@cryptsoft.com). | ||||
|  * The implementation was written so as to conform with Netscapes SSL. | ||||
|  *  | ||||
|  * This library is free for commercial and non-commercial use as long as | ||||
|  * the following conditions are aheared to.  The following conditions | ||||
|  * apply to all code found in this distribution, be it the RC4, RSA, | ||||
|  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation | ||||
|  * included with this distribution is covered by the same copyright terms | ||||
|  * except that the holder is Tim Hudson (tjh@cryptsoft.com). | ||||
|  *  | ||||
|  * Copyright remains Eric Young's, and as such any Copyright notices in | ||||
|  * the code are not to be removed. | ||||
|  * If this package is used in a product, Eric Young should be given attribution | ||||
|  * as the author of the parts of the library used. | ||||
|  * This can be in the form of a textual message at program startup or | ||||
|  * in documentation (online or textual) provided with the package. | ||||
|  *  | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * 1. Redistributions of source code must retain the copyright | ||||
|  *    notice, this list of conditions and the following disclaimer. | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in the | ||||
|  *    documentation and/or other materials provided with the distribution. | ||||
|  * 3. All advertising materials mentioning features or use of this software | ||||
|  *    must display the following acknowledgement: | ||||
|  *    "This product includes cryptographic software written by | ||||
|  *     Eric Young (eay@cryptsoft.com)" | ||||
|  *    The word 'cryptographic' can be left out if the rouines from the library | ||||
|  *    being used are not cryptographic related :-). | ||||
|  * 4. If you include any Windows specific code (or a derivative thereof) from  | ||||
|  *    the apps directory (application code) you must include an acknowledgement: | ||||
|  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | ||||
|  *  | ||||
|  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND | ||||
|  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||||
|  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | ||||
|  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||||
|  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||||
|  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||||
|  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||||
|  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||||
|  * SUCH DAMAGE. | ||||
|  *  | ||||
|  * The licence and distribution terms for any publically available version or | ||||
|  * derivative of this code cannot be changed.  i.e. this code cannot simply be | ||||
|  * copied and put under another distribution licence | ||||
|  * [including the GNU Public Licence.] | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <string.h> | ||||
| #include <time.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/fips.h> | ||||
| 
 | ||||
| #ifdef OPENSSL_FIPS | ||||
| 
 | ||||
| extern int fips_check_rsa(RSA *rsa); | ||||
| 
 | ||||
| 
 | ||||
| /* X9.31 RSA key derivation and generation */ | ||||
| 
 | ||||
| int RSA_X931_derive_ex(RSA *rsa, BIGNUM *p1, BIGNUM *p2, BIGNUM *q1, BIGNUM *q2, | ||||
| 			const BIGNUM *Xp1, const BIGNUM *Xp2, const BIGNUM *Xp, | ||||
| 			const BIGNUM *Xq1, const BIGNUM *Xq2, const BIGNUM *Xq, | ||||
| 			const BIGNUM *e, BN_GENCB *cb) | ||||
| 	{ | ||||
| 	BIGNUM *r0=NULL,*r1=NULL,*r2=NULL,*r3=NULL; | ||||
| 	BN_CTX *ctx=NULL,*ctx2=NULL; | ||||
| 
 | ||||
| 	if (!rsa)  | ||||
| 		goto err; | ||||
| 
 | ||||
| 	ctx = BN_CTX_new(); | ||||
| 	BN_CTX_start(ctx); | ||||
| 	if (!ctx)  | ||||
| 		goto err; | ||||
| 
 | ||||
| 	r0 = BN_CTX_get(ctx); | ||||
| 	r1 = BN_CTX_get(ctx); | ||||
| 	r2 = BN_CTX_get(ctx); | ||||
| 	r3 = BN_CTX_get(ctx); | ||||
| 
 | ||||
| 	if (r3 == NULL) | ||||
| 		goto err; | ||||
| 	if (!rsa->e) | ||||
| 		{ | ||||
| 		rsa->e = BN_dup(e); | ||||
| 		if (!rsa->e) | ||||
| 			goto err; | ||||
| 		} | ||||
| 	else | ||||
| 		e = rsa->e; | ||||
| 
 | ||||
| 	/* If not all parameters present only calculate what we can.
 | ||||
| 	 * This allows test programs to output selective parameters. | ||||
| 	 */ | ||||
| 
 | ||||
| 	if (Xp && !rsa->p) | ||||
| 		{ | ||||
| 		rsa->p = BN_new(); | ||||
| 		if (!rsa->p) | ||||
| 			goto err; | ||||
| 
 | ||||
| 		if (!BN_X931_derive_prime_ex(rsa->p, p1, p2, | ||||
| 					Xp, Xp1, Xp2, e, ctx, cb)) | ||||
| 			goto err; | ||||
| 		} | ||||
| 
 | ||||
| 	if (Xq && !rsa->q) | ||||
| 		{ | ||||
| 		rsa->q = BN_new(); | ||||
| 		if (!rsa->q) | ||||
| 			goto err; | ||||
| 		if (!BN_X931_derive_prime_ex(rsa->q, q1, q2, | ||||
| 					Xq, Xq1, Xq2, e, ctx, cb)) | ||||
| 			goto err; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!rsa->p || !rsa->q) | ||||
| 		{ | ||||
| 		BN_CTX_end(ctx); | ||||
| 		BN_CTX_free(ctx); | ||||
| 		return 2; | ||||
| 		} | ||||
| 
 | ||||
| 	/* Since both primes are set we can now calculate all remaining 
 | ||||
| 	 * components. | ||||
| 	 */ | ||||
| 
 | ||||
| 	/* calculate n */ | ||||
| 	rsa->n=BN_new(); | ||||
| 	if (rsa->n == NULL) | ||||
| 		goto err; | ||||
| 	if (!BN_mul(rsa->n,rsa->p,rsa->q,ctx)) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	/* calculate d */ | ||||
| 	if (!BN_sub(r1,rsa->p,BN_value_one())) | ||||
| 		goto err;	/* p-1 */ | ||||
| 	if (!BN_sub(r2,rsa->q,BN_value_one())) | ||||
| 		goto err;	/* q-1 */ | ||||
| 	if (!BN_mul(r0,r1,r2,ctx)) | ||||
| 		goto err;	/* (p-1)(q-1) */ | ||||
| 
 | ||||
| 	if (!BN_gcd(r3, r1, r2, ctx)) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	if (!BN_div(r0, NULL, r0, r3, ctx)) | ||||
| 		goto err;	/* LCM((p-1)(q-1)) */ | ||||
| 
 | ||||
| 	ctx2 = BN_CTX_new(); | ||||
| 	if (!ctx2) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	rsa->d=BN_mod_inverse(NULL,rsa->e,r0,ctx2);	/* d */ | ||||
| 	if (rsa->d == NULL) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	/* calculate d mod (p-1) */ | ||||
| 	rsa->dmp1=BN_new(); | ||||
| 	if (rsa->dmp1 == NULL) | ||||
| 		goto err; | ||||
| 	if (!BN_mod(rsa->dmp1,rsa->d,r1,ctx)) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	/* calculate d mod (q-1) */ | ||||
| 	rsa->dmq1=BN_new(); | ||||
| 	if (rsa->dmq1 == NULL) | ||||
| 		goto err; | ||||
| 	if (!BN_mod(rsa->dmq1,rsa->d,r2,ctx)) | ||||
| 		goto err; | ||||
| 
 | ||||
| 	/* calculate inverse of q mod p */ | ||||
| 	rsa->iqmp=BN_mod_inverse(NULL,rsa->q,rsa->p,ctx2); | ||||
| 
 | ||||
| 	err: | ||||
| 	if (ctx) | ||||
| 		{ | ||||
| 		BN_CTX_end(ctx); | ||||
| 		BN_CTX_free(ctx); | ||||
| 		} | ||||
| 	if (ctx2) | ||||
| 		BN_CTX_free(ctx2); | ||||
| 	/* If this is set all calls successful */ | ||||
| 	if (rsa->iqmp != NULL) | ||||
| 		return 1; | ||||
| 
 | ||||
| 	return 0; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| int RSA_X931_generate_key_ex(RSA *rsa, int bits, const BIGNUM *e, BN_GENCB *cb) | ||||
| 	{ | ||||
| 	int ok = 0; | ||||
| 	BIGNUM *Xp = NULL, *Xq = NULL; | ||||
| 	BN_CTX *ctx = NULL; | ||||
| 	 | ||||
| 	if (bits < OPENSSL_RSA_FIPS_MIN_MODULUS_BITS) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_RSA_X931_GENERATE_KEY_EX,FIPS_R_KEY_TOO_SHORT); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 
 | ||||
| 	if (bits & 0xff) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_RSA_X931_GENERATE_KEY_EX,FIPS_R_INVALID_KEY_LENGTH); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 
 | ||||
| 	if(FIPS_selftest_failed()) | ||||
| 	    { | ||||
| 	    FIPSerr(FIPS_F_RSA_X931_GENERATE_KEY_EX,FIPS_R_FIPS_SELFTEST_FAILED); | ||||
| 	    return 0; | ||||
| 	    } | ||||
| 
 | ||||
| 	ctx = BN_CTX_new(); | ||||
| 	if (!ctx) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	BN_CTX_start(ctx); | ||||
| 	Xp = BN_CTX_get(ctx); | ||||
| 	Xq = BN_CTX_get(ctx); | ||||
| 	if (!BN_X931_generate_Xpq(Xp, Xq, bits, ctx)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	rsa->p = BN_new(); | ||||
| 	rsa->q = BN_new(); | ||||
| 	if (!rsa->p || !rsa->q) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	/* Generate two primes from Xp, Xq */ | ||||
| 
 | ||||
| 	if (!BN_X931_generate_prime_ex(rsa->p, NULL, NULL, NULL, NULL, Xp, | ||||
| 					e, ctx, cb)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if (!BN_X931_generate_prime_ex(rsa->q, NULL, NULL, NULL, NULL, Xq, | ||||
| 					e, ctx, cb)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	/* Since rsa->p and rsa->q are valid this call will just derive
 | ||||
| 	 * remaining RSA components. | ||||
| 	 */ | ||||
| 
 | ||||
| 	if (!RSA_X931_derive_ex(rsa, NULL, NULL, NULL, NULL, | ||||
| 				NULL, NULL, NULL, NULL, NULL, NULL, e, cb)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if(!fips_check_rsa(rsa)) | ||||
| 	    goto error; | ||||
| 
 | ||||
| 	ok = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 	if (ctx) | ||||
| 		{ | ||||
| 		BN_CTX_end(ctx); | ||||
| 		BN_CTX_free(ctx); | ||||
| 		} | ||||
| 
 | ||||
| 	if (ok) | ||||
| 		return 1; | ||||
| 
 | ||||
| 	return 0; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,388 @@ | |||
| /* fips_rsagtest.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2005. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005,2007 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <ctype.h> | ||||
| #include <string.h> | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/x509v3.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS RSA support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| int rsa_test(FILE *out, FILE *in); | ||||
| static int rsa_printkey1(FILE *out, RSA *rsa, | ||||
| 		BIGNUM *Xp1, BIGNUM *Xp2, BIGNUM *Xp, | ||||
| 		BIGNUM *e); | ||||
| static int rsa_printkey2(FILE *out, RSA *rsa, | ||||
| 		BIGNUM *Xq1, BIGNUM *Xq2, BIGNUM *Xq); | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| 	{ | ||||
| 	FILE *in = NULL, *out = NULL; | ||||
| 
 | ||||
| 	int ret = 1; | ||||
| 
 | ||||
| 	fips_set_error_print(); | ||||
| 	if(!FIPS_mode_set(1)) | ||||
| 		goto end; | ||||
| 
 | ||||
| 	if (argc == 1) | ||||
| 		in = stdin; | ||||
| 	else | ||||
| 		in = fopen(argv[1], "r"); | ||||
| 
 | ||||
| 	if (argc < 2) | ||||
| 		out = stdout; | ||||
| 	else | ||||
| 		out = fopen(argv[2], "w"); | ||||
| 
 | ||||
| 	if (!in) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL input initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!out) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL output initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!rsa_test(out, in)) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL RSAGTEST file processing error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 	else | ||||
| 		ret = 0; | ||||
| 
 | ||||
| 	end: | ||||
| 
 | ||||
| 	if (in && (in != stdin)) | ||||
| 		fclose(in); | ||||
| 	if (out && (out != stdout)) | ||||
| 		fclose(out); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| #define RSA_TEST_MAXLINELEN	10240 | ||||
| 
 | ||||
| int rsa_test(FILE *out, FILE *in) | ||||
| 	{ | ||||
| 	char *linebuf, *olinebuf, *p, *q; | ||||
| 	char *keyword, *value; | ||||
| 	RSA *rsa = NULL; | ||||
| 	BIGNUM *Xp1 = NULL, *Xp2 = NULL, *Xp = NULL; | ||||
| 	BIGNUM *Xq1 = NULL, *Xq2 = NULL, *Xq = NULL; | ||||
| 	BIGNUM *e = NULL; | ||||
| 	int ret = 0; | ||||
| 	int lnum = 0; | ||||
| 
 | ||||
| 	olinebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 	linebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 
 | ||||
| 	if (!linebuf || !olinebuf) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	while (fgets(olinebuf, RSA_TEST_MAXLINELEN, in)) | ||||
| 		{ | ||||
| 		lnum++; | ||||
| 		strcpy(linebuf, olinebuf); | ||||
| 		keyword = linebuf; | ||||
| 		/* Skip leading space */ | ||||
| 		while (isspace((unsigned char)*keyword)) | ||||
| 			keyword++; | ||||
| 
 | ||||
| 		/* Look for = sign */ | ||||
| 		p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 		/* If no = or starts with [ (for [foo = bar] line) just copy */ | ||||
| 		if (!p || *keyword=='[') | ||||
| 			{ | ||||
| 			if (fputs(olinebuf, out) < 0) | ||||
| 				goto error; | ||||
| 			continue; | ||||
| 			} | ||||
| 
 | ||||
| 		q = p - 1; | ||||
| 
 | ||||
| 		/* Remove trailing space */ | ||||
| 		while (isspace((unsigned char)*q)) | ||||
| 			*q-- = 0; | ||||
| 
 | ||||
| 		*p = 0; | ||||
| 		value = p + 1; | ||||
| 
 | ||||
| 		/* Remove leading space from value */ | ||||
| 		while (isspace((unsigned char)*value)) | ||||
| 			value++; | ||||
| 
 | ||||
| 		/* Remove trailing space from value */ | ||||
| 		p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 		while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 			*p-- = 0; | ||||
| 
 | ||||
| 		if (!strcmp(keyword, "xp1")) | ||||
| 			{ | ||||
| 			if (Xp1 || !do_hex2bn(&Xp1,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "xp2")) | ||||
| 			{ | ||||
| 			if (Xp2 || !do_hex2bn(&Xp2,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Xp")) | ||||
| 			{ | ||||
| 			if (Xp || !do_hex2bn(&Xp,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "xq1")) | ||||
| 			{ | ||||
| 			if (Xq1 || !do_hex2bn(&Xq1,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "xq2")) | ||||
| 			{ | ||||
| 			if (Xq2 || !do_hex2bn(&Xq2,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Xq")) | ||||
| 			{ | ||||
| 			if (Xq || !do_hex2bn(&Xq,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "e")) | ||||
| 			{ | ||||
| 			if (e || !do_hex2bn(&e,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "p1")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "p2")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "p")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "q1")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "q2")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "q")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "n")) | ||||
| 			continue; | ||||
| 		else if (!strcmp(keyword, "d")) | ||||
| 			continue; | ||||
| 		else | ||||
| 			goto parse_error; | ||||
| 
 | ||||
| 		fputs(olinebuf, out); | ||||
| 
 | ||||
| 		if (e && Xp1 && Xp2 && Xp) | ||||
| 			{ | ||||
| 			rsa = FIPS_rsa_new(); | ||||
| 			if (!rsa) | ||||
| 				goto error; | ||||
| 			if (!rsa_printkey1(out, rsa, Xp1, Xp2, Xp, e)) | ||||
| 				goto error; | ||||
| 			BN_free(Xp1); | ||||
| 			Xp1 = NULL; | ||||
| 			BN_free(Xp2); | ||||
| 			Xp2 = NULL; | ||||
| 			BN_free(Xp); | ||||
| 			Xp = NULL; | ||||
| 			BN_free(e); | ||||
| 			e = NULL; | ||||
| 			} | ||||
| 
 | ||||
| 		if (rsa && Xq1 && Xq2 && Xq) | ||||
| 			{ | ||||
| 			if (!rsa_printkey2(out, rsa, Xq1, Xq2, Xq)) | ||||
| 				goto error; | ||||
| 			BN_free(Xq1); | ||||
| 			Xq1 = NULL; | ||||
| 			BN_free(Xq2); | ||||
| 			Xq2 = NULL; | ||||
| 			BN_free(Xq); | ||||
| 			Xq = NULL; | ||||
| 			FIPS_rsa_free(rsa); | ||||
| 			rsa = NULL; | ||||
| 			} | ||||
| 		} | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 
 | ||||
| 	if (olinebuf) | ||||
| 		OPENSSL_free(olinebuf); | ||||
| 	if (linebuf) | ||||
| 		OPENSSL_free(linebuf); | ||||
| 
 | ||||
| 	if (Xp1) | ||||
| 		BN_free(Xp1); | ||||
| 	if (Xp2) | ||||
| 		BN_free(Xp2); | ||||
| 	if (Xp) | ||||
| 		BN_free(Xp); | ||||
| 	if (Xq1) | ||||
| 		BN_free(Xq1); | ||||
| 	if (Xq1) | ||||
| 		BN_free(Xq1); | ||||
| 	if (Xq2) | ||||
| 		BN_free(Xq2); | ||||
| 	if (Xq) | ||||
| 		BN_free(Xq); | ||||
| 	if (e) | ||||
| 		BN_free(e); | ||||
| 	if (rsa) | ||||
| 		FIPS_rsa_free(rsa); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	parse_error: | ||||
| 
 | ||||
| 	fprintf(stderr, "FATAL parse error processing line %d\n", lnum); | ||||
| 
 | ||||
| 	goto error; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| static int rsa_printkey1(FILE *out, RSA *rsa, | ||||
| 		BIGNUM *Xp1, BIGNUM *Xp2, BIGNUM *Xp, | ||||
| 		BIGNUM *e) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	BIGNUM *p1 = NULL, *p2 = NULL; | ||||
| 	p1 = BN_new(); | ||||
| 	p2 = BN_new(); | ||||
| 	if (!p1 || !p2) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if (!RSA_X931_derive_ex(rsa, p1, p2, NULL, NULL, Xp1, Xp2, Xp, | ||||
| 						NULL, NULL, NULL, e, NULL)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	do_bn_print_name(out, "p1", p1); | ||||
| 	do_bn_print_name(out, "p2", p2); | ||||
| 	do_bn_print_name(out, "p", rsa->p); | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 	if (p1) | ||||
| 		BN_free(p1); | ||||
| 	if (p2) | ||||
| 		BN_free(p2); | ||||
| 
 | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| static int rsa_printkey2(FILE *out, RSA *rsa, | ||||
| 		BIGNUM *Xq1, BIGNUM *Xq2, BIGNUM *Xq) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	BIGNUM *q1 = NULL, *q2 = NULL; | ||||
| 	q1 = BN_new(); | ||||
| 	q2 = BN_new(); | ||||
| 	if (!q1 || !q2) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if (!RSA_X931_derive_ex(rsa, NULL, NULL, q1, q2, NULL, NULL, NULL, | ||||
| 						Xq1, Xq2, Xq, NULL, NULL)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	do_bn_print_name(out, "q1", q1); | ||||
| 	do_bn_print_name(out, "q2", q2); | ||||
| 	do_bn_print_name(out, "q", rsa->q); | ||||
| 	do_bn_print_name(out, "n", rsa->n); | ||||
| 	do_bn_print_name(out, "d", rsa->d); | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 	if (q1) | ||||
| 		BN_free(q1); | ||||
| 	if (q2) | ||||
| 		BN_free(q2); | ||||
| 
 | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| #endif | ||||
|  | @ -0,0 +1,366 @@ | |||
| /* fips_rsastest.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2005. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <ctype.h> | ||||
| #include <string.h> | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/bn.h> | ||||
| #include <openssl/x509v3.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS RSA support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/fips.h> | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| static int rsa_stest(FILE *out, FILE *in, int Saltlen); | ||||
| static int rsa_printsig(FILE *out, RSA *rsa, const EVP_MD *dgst, | ||||
| 		unsigned char *Msg, long Msglen, int Saltlen); | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| 	{ | ||||
| 	FILE *in = NULL, *out = NULL; | ||||
| 
 | ||||
| 	int ret = 1, Saltlen = -1; | ||||
| 
 | ||||
| 	fips_set_error_print(); | ||||
| 	if(!FIPS_mode_set(1)) | ||||
| 		goto end; | ||||
| 
 | ||||
| 	if ((argc > 2) && !strcmp("-saltlen", argv[1])) | ||||
| 		{ | ||||
| 		Saltlen = atoi(argv[2]); | ||||
| 		if (Saltlen < 0) | ||||
| 			{ | ||||
| 			fprintf(stderr, "FATAL: Invalid salt length\n"); | ||||
| 			goto end; | ||||
| 			} | ||||
| 		argc -= 2; | ||||
| 		argv += 2; | ||||
| 		} | ||||
| 	else if ((argc > 1) && !strcmp("-x931", argv[1])) | ||||
| 		{ | ||||
| 		Saltlen = -2; | ||||
| 		argc--; | ||||
| 		argv++; | ||||
| 		} | ||||
| 
 | ||||
| 	if (argc == 1) | ||||
| 		in = stdin; | ||||
| 	else | ||||
| 		in = fopen(argv[1], "r"); | ||||
| 
 | ||||
| 	if (argc < 2) | ||||
| 		out = stdout; | ||||
| 	else | ||||
| 		out = fopen(argv[2], "w"); | ||||
| 
 | ||||
| 	if (!in) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL input initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!out) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL output initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!rsa_stest(out, in, Saltlen)) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL RSASTEST file processing error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 	else | ||||
| 		ret = 0; | ||||
| 
 | ||||
| 	end: | ||||
| 
 | ||||
| 	if (in && (in != stdin)) | ||||
| 		fclose(in); | ||||
| 	if (out && (out != stdout)) | ||||
| 		fclose(out); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| #define RSA_TEST_MAXLINELEN	10240 | ||||
| 
 | ||||
| int rsa_stest(FILE *out, FILE *in, int Saltlen) | ||||
| 	{ | ||||
| 	char *linebuf, *olinebuf, *p, *q; | ||||
| 	char *keyword, *value; | ||||
| 	RSA *rsa = NULL; | ||||
| 	const EVP_MD *dgst = NULL; | ||||
| 	unsigned char *Msg = NULL; | ||||
| 	long Msglen = -1; | ||||
| 	int keylen = -1, current_keylen = -1; | ||||
| 	int ret = 0; | ||||
| 	int lnum = 0; | ||||
| 
 | ||||
| 	olinebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 	linebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 
 | ||||
| 	if (!linebuf || !olinebuf) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	while (fgets(olinebuf, RSA_TEST_MAXLINELEN, in)) | ||||
| 		{ | ||||
| 		lnum++; | ||||
| 		strcpy(linebuf, olinebuf); | ||||
| 		keyword = linebuf; | ||||
| 		/* Skip leading space */ | ||||
| 		while (isspace((unsigned char)*keyword)) | ||||
| 			keyword++; | ||||
| 
 | ||||
| 		/* Look for = sign */ | ||||
| 		p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 		/* If no = just copy */ | ||||
| 		if (!p) | ||||
| 			{ | ||||
| 			if (fputs(olinebuf, out) < 0) | ||||
| 				goto error; | ||||
| 			continue; | ||||
| 			} | ||||
| 
 | ||||
| 		q = p - 1; | ||||
| 
 | ||||
| 		/* Remove trailing space */ | ||||
| 		while (isspace((unsigned char)*q)) | ||||
| 			*q-- = 0; | ||||
| 
 | ||||
| 		*p = 0; | ||||
| 		value = p + 1; | ||||
| 
 | ||||
| 		/* Remove leading space from value */ | ||||
| 		while (isspace((unsigned char)*value)) | ||||
| 			value++; | ||||
| 
 | ||||
| 		/* Remove trailing space from value */ | ||||
| 		p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 		while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 			*p-- = 0; | ||||
| 
 | ||||
| 		/* Look for [mod = XXX] for key length */ | ||||
| 
 | ||||
| 		if (!strcmp(keyword, "[mod")) | ||||
| 			{ | ||||
| 			p = value + strlen(value) - 1; | ||||
| 			if (*p != ']') | ||||
| 				goto parse_error; | ||||
| 			*p = 0; | ||||
| 			keylen = atoi(value); | ||||
| 			if (keylen < 0) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "SHAAlg")) | ||||
| 			{ | ||||
| 			if (!strcmp(value, "SHA1")) | ||||
| 				dgst = EVP_sha1(); | ||||
| 			else if (!strcmp(value, "SHA224")) | ||||
| 				dgst = EVP_sha224(); | ||||
| 			else if (!strcmp(value, "SHA256")) | ||||
| 				dgst = EVP_sha256(); | ||||
| 			else if (!strcmp(value, "SHA384")) | ||||
| 				dgst = EVP_sha384(); | ||||
| 			else if (!strcmp(value, "SHA512")) | ||||
| 				dgst = EVP_sha512(); | ||||
| 			else | ||||
| 				{ | ||||
| 				fprintf(stderr, | ||||
| 					"FATAL: unsupported algorithm \"%s\"\n", | ||||
| 								value); | ||||
| 				goto parse_error; | ||||
| 				} | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Msg")) | ||||
| 			{ | ||||
| 			if (Msg) | ||||
| 				goto parse_error; | ||||
| 			if (strlen(value) & 1) | ||||
| 				*(--value) = '0'; | ||||
| 			Msg = hex2bin_m(value, &Msglen); | ||||
| 			if (!Msg) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 
 | ||||
| 		fputs(olinebuf, out); | ||||
| 
 | ||||
| 		/* If key length has changed, generate and output public
 | ||||
| 		 * key components of new RSA private key. | ||||
| 		 */ | ||||
| 
 | ||||
| 		if (keylen != current_keylen) | ||||
| 			{ | ||||
| 			BIGNUM *bn_e; | ||||
| 			if (rsa) | ||||
| 				FIPS_rsa_free(rsa); | ||||
| 			rsa = FIPS_rsa_new(); | ||||
| 			if (!rsa) | ||||
| 				goto error; | ||||
| 			bn_e = BN_new(); | ||||
| 			if (!bn_e || !BN_set_word(bn_e, 0x1001)) | ||||
| 				goto error; | ||||
| 			if (!RSA_X931_generate_key_ex(rsa, keylen, bn_e, NULL)) | ||||
| 				goto error; | ||||
| 			BN_free(bn_e); | ||||
| 			fputs("n = ", out); | ||||
| 			do_bn_print(out, rsa->n); | ||||
| 			fputs("\ne = ", out); | ||||
| 			do_bn_print(out, rsa->e); | ||||
| 			fputs("\n", out); | ||||
| 			current_keylen = keylen; | ||||
| 			} | ||||
| 
 | ||||
| 		if (Msg && dgst) | ||||
| 			{ | ||||
| 			if (!rsa_printsig(out, rsa, dgst, Msg, Msglen, | ||||
| 								Saltlen)) | ||||
| 				goto error; | ||||
| 			OPENSSL_free(Msg); | ||||
| 			Msg = NULL; | ||||
| 			} | ||||
| 
 | ||||
| 		} | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 
 | ||||
| 	if (olinebuf) | ||||
| 		OPENSSL_free(olinebuf); | ||||
| 	if (linebuf) | ||||
| 		OPENSSL_free(linebuf); | ||||
| 	if (rsa) | ||||
| 		FIPS_rsa_free(rsa); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	parse_error: | ||||
| 
 | ||||
| 	fprintf(stderr, "FATAL parse error processing line %d\n", lnum); | ||||
| 
 | ||||
| 	goto error; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| static int rsa_printsig(FILE *out, RSA *rsa, const EVP_MD *dgst, | ||||
| 		unsigned char *Msg, long Msglen, int Saltlen) | ||||
| 	{ | ||||
| 	int ret = 0; | ||||
| 	unsigned char *sigbuf = NULL; | ||||
| 	int i, siglen, pad_mode; | ||||
| 	/* EVP_PKEY structure */ | ||||
| 	EVP_MD_CTX ctx; | ||||
| 
 | ||||
| 	siglen = RSA_size(rsa); | ||||
| 	sigbuf = OPENSSL_malloc(siglen); | ||||
| 	if (!sigbuf) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	EVP_MD_CTX_init(&ctx); | ||||
| 
 | ||||
| 	if (Saltlen >= 0) | ||||
| 		pad_mode = RSA_PKCS1_PSS_PADDING; | ||||
| 	else if (Saltlen == -2) | ||||
| 		pad_mode = RSA_X931_PADDING; | ||||
| 	else | ||||
| 		pad_mode = RSA_PKCS1_PADDING; | ||||
| 
 | ||||
| 	if (!EVP_DigestInit_ex(&ctx, dgst, NULL)) | ||||
| 		goto error; | ||||
| 	if (!EVP_DigestUpdate(&ctx, Msg, Msglen)) | ||||
| 		goto error; | ||||
| 	if (!FIPS_rsa_sign_ctx(rsa, &ctx, pad_mode, Saltlen, NULL, | ||||
| 				sigbuf, (unsigned int *)&siglen)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	EVP_MD_CTX_cleanup(&ctx); | ||||
| 
 | ||||
| 	fputs("S = ", out); | ||||
| 
 | ||||
| 	for (i = 0; i < siglen; i++) | ||||
| 		fprintf(out, "%02X", sigbuf[i]); | ||||
| 
 | ||||
| 	fputs("\n", out); | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 
 | ||||
| 	return ret; | ||||
| 	} | ||||
| #endif | ||||
|  | @ -0,0 +1,375 @@ | |||
| /* fips_rsavtest.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project 2005. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2005 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| #define OPENSSL_FIPSEVP | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <ctype.h> | ||||
| #include <string.h> | ||||
| #include <openssl/bio.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/hmac.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/x509v3.h> | ||||
| #include <openssl/bn.h> | ||||
| 
 | ||||
| #ifndef OPENSSL_FIPS | ||||
| 
 | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
|     printf("No FIPS RSA support\n"); | ||||
|     return(0); | ||||
| } | ||||
| 
 | ||||
| #else | ||||
| 
 | ||||
| #include <openssl/rsa.h> | ||||
| #include <openssl/fips.h> | ||||
| 
 | ||||
| #include "fips_utl.h" | ||||
| 
 | ||||
| int rsa_test(FILE *out, FILE *in, int saltlen); | ||||
| static int rsa_printver(FILE *out, | ||||
| 		BIGNUM *n, BIGNUM *e, | ||||
| 		const EVP_MD *dgst, | ||||
| 		unsigned char *Msg, long Msglen, | ||||
| 		unsigned char *S, long Slen, int Saltlen); | ||||
| 
 | ||||
| int main(int argc, char **argv) | ||||
| 	{ | ||||
| 	FILE *in = NULL, *out = NULL; | ||||
| 
 | ||||
| 	int ret = 1; | ||||
| 	int Saltlen = -1; | ||||
| 
 | ||||
| 	fips_set_error_print(); | ||||
| 	if(!FIPS_mode_set(1)) | ||||
| 		goto end; | ||||
| 
 | ||||
| 	if ((argc > 2) && !strcmp("-saltlen", argv[1])) | ||||
| 		{ | ||||
| 		Saltlen = atoi(argv[2]); | ||||
| 		if (Saltlen < 0) | ||||
| 			{ | ||||
| 			fprintf(stderr, "FATAL: Invalid salt length\n"); | ||||
| 			goto end; | ||||
| 			} | ||||
| 		argc -= 2; | ||||
| 		argv += 2; | ||||
| 		} | ||||
| 	else if ((argc > 1) && !strcmp("-x931", argv[1])) | ||||
| 		{ | ||||
| 		Saltlen = -2; | ||||
| 		argc--; | ||||
| 		argv++; | ||||
| 		} | ||||
| 
 | ||||
| 	if (argc == 1) | ||||
| 		in = stdin; | ||||
| 	else | ||||
| 		in = fopen(argv[1], "r"); | ||||
| 
 | ||||
| 	if (argc < 2) | ||||
| 		out = stdout; | ||||
| 	else | ||||
| 		out = fopen(argv[2], "w"); | ||||
| 
 | ||||
| 	if (!in) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL input initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!out) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL output initialization error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 
 | ||||
| 	if (!rsa_test(out, in, Saltlen)) | ||||
| 		{ | ||||
| 		fprintf(stderr, "FATAL RSAVTEST file processing error\n"); | ||||
| 		goto end; | ||||
| 		} | ||||
| 	else | ||||
| 		ret = 0; | ||||
| 
 | ||||
| 	end: | ||||
| 
 | ||||
| 	if (in && (in != stdin)) | ||||
| 		fclose(in); | ||||
| 	if (out && (out != stdout)) | ||||
| 		fclose(out); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| #define RSA_TEST_MAXLINELEN	10240 | ||||
| 
 | ||||
| int rsa_test(FILE *out, FILE *in, int Saltlen) | ||||
| 	{ | ||||
| 	char *linebuf, *olinebuf, *p, *q; | ||||
| 	char *keyword, *value; | ||||
| 	const EVP_MD *dgst = NULL; | ||||
| 	BIGNUM *n = NULL, *e = NULL; | ||||
| 	unsigned char *Msg = NULL, *S = NULL; | ||||
| 	long Msglen, Slen; | ||||
| 	int ret = 0; | ||||
| 	int lnum = 0; | ||||
| 
 | ||||
| 	olinebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 	linebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN); | ||||
| 
 | ||||
| 	if (!linebuf || !olinebuf) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	while (fgets(olinebuf, RSA_TEST_MAXLINELEN, in)) | ||||
| 		{ | ||||
| 		lnum++; | ||||
| 		strcpy(linebuf, olinebuf); | ||||
| 		keyword = linebuf; | ||||
| 		/* Skip leading space */ | ||||
| 		while (isspace((unsigned char)*keyword)) | ||||
| 			keyword++; | ||||
| 
 | ||||
| 		/* Look for = sign */ | ||||
| 		p = strchr(linebuf, '='); | ||||
| 
 | ||||
| 		/* If no = or starts with [ (for [foo = bar] line) just copy */ | ||||
| 		if (!p || *keyword=='[') | ||||
| 			{ | ||||
| 			if (fputs(olinebuf, out) < 0) | ||||
| 				goto error; | ||||
| 			continue; | ||||
| 			} | ||||
| 
 | ||||
| 		q = p - 1; | ||||
| 
 | ||||
| 		/* Remove trailing space */ | ||||
| 		while (isspace((unsigned char)*q)) | ||||
| 			*q-- = 0; | ||||
| 
 | ||||
| 		*p = 0; | ||||
| 		value = p + 1; | ||||
| 
 | ||||
| 		/* Remove leading space from value */ | ||||
| 		while (isspace((unsigned char)*value)) | ||||
| 			value++; | ||||
| 
 | ||||
| 		/* Remove trailing space from value */ | ||||
| 		p = value + strlen(value) - 1; | ||||
| 
 | ||||
| 		while (*p == '\n' || isspace((unsigned char)*p)) | ||||
| 			*p-- = 0; | ||||
| 
 | ||||
| 		if (!strcmp(keyword, "n")) | ||||
| 			{ | ||||
| 			if (!do_hex2bn(&n,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "e")) | ||||
| 			{ | ||||
| 			if (!do_hex2bn(&e,value)) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "SHAAlg")) | ||||
| 			{ | ||||
| 			if (!strcmp(value, "SHA1")) | ||||
| 				dgst = EVP_sha1(); | ||||
| 			else if (!strcmp(value, "SHA224")) | ||||
| 				dgst = EVP_sha224(); | ||||
| 			else if (!strcmp(value, "SHA256")) | ||||
| 				dgst = EVP_sha256(); | ||||
| 			else if (!strcmp(value, "SHA384")) | ||||
| 				dgst = EVP_sha384(); | ||||
| 			else if (!strcmp(value, "SHA512")) | ||||
| 				dgst = EVP_sha512(); | ||||
| 			else | ||||
| 				{ | ||||
| 				fprintf(stderr, | ||||
| 					"FATAL: unsupported algorithm \"%s\"\n", | ||||
| 								value); | ||||
| 				goto parse_error; | ||||
| 				} | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Msg")) | ||||
| 			{ | ||||
| 			if (Msg) | ||||
| 				goto parse_error; | ||||
| 			if (strlen(value) & 1) | ||||
| 				*(--value) = '0'; | ||||
| 			Msg = hex2bin_m(value, &Msglen); | ||||
| 			if (!Msg) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "S")) | ||||
| 			{ | ||||
| 			if (S) | ||||
| 				goto parse_error; | ||||
| 			if (strlen(value) & 1) | ||||
| 				*(--value) = '0'; | ||||
| 			S = hex2bin_m(value, &Slen); | ||||
| 			if (!S) | ||||
| 				goto parse_error; | ||||
| 			} | ||||
| 		else if (!strcmp(keyword, "Result")) | ||||
| 			continue; | ||||
| 		else | ||||
| 			goto parse_error; | ||||
| 
 | ||||
| 		fputs(olinebuf, out); | ||||
| 
 | ||||
| 		if (n && e && Msg && S && dgst) | ||||
| 			{ | ||||
| 			if (!rsa_printver(out, n, e, dgst, | ||||
| 					Msg, Msglen, S, Slen, Saltlen)) | ||||
| 				goto error; | ||||
| 			OPENSSL_free(Msg); | ||||
| 			Msg = NULL; | ||||
| 			OPENSSL_free(S); | ||||
| 			S = NULL; | ||||
| 			} | ||||
| 
 | ||||
| 		} | ||||
| 
 | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 
 | ||||
| 	error: | ||||
| 
 | ||||
| 	if (olinebuf) | ||||
| 		OPENSSL_free(olinebuf); | ||||
| 	if (linebuf) | ||||
| 		OPENSSL_free(linebuf); | ||||
| 	if (n) | ||||
| 		BN_free(n); | ||||
| 	if (e) | ||||
| 		BN_free(e); | ||||
| 
 | ||||
| 	return ret; | ||||
| 
 | ||||
| 	parse_error: | ||||
| 
 | ||||
| 	fprintf(stderr, "FATAL parse error processing line %d\n", lnum); | ||||
| 
 | ||||
| 	goto error; | ||||
| 
 | ||||
| 	} | ||||
| 
 | ||||
| static int rsa_printver(FILE *out, | ||||
| 		BIGNUM *n, BIGNUM *e, | ||||
| 		const EVP_MD *dgst, | ||||
| 		unsigned char *Msg, long Msglen, | ||||
| 		unsigned char *S, long Slen, int Saltlen) | ||||
| 	{ | ||||
| 	int ret = 0, r, pad_mode; | ||||
| 	/* Setup RSA and EVP_PKEY structures */ | ||||
| 	RSA *rsa_pubkey = NULL; | ||||
| 	EVP_MD_CTX ctx; | ||||
| 	unsigned char *buf = NULL; | ||||
| 	rsa_pubkey = FIPS_rsa_new(); | ||||
| 	if (!rsa_pubkey) | ||||
| 		goto error; | ||||
| 	rsa_pubkey->n = BN_dup(n); | ||||
| 	rsa_pubkey->e = BN_dup(e); | ||||
| 	if (!rsa_pubkey->n || !rsa_pubkey->e) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	EVP_MD_CTX_init(&ctx); | ||||
| 
 | ||||
| 	if (Saltlen >= 0) | ||||
| 		pad_mode = RSA_PKCS1_PSS_PADDING; | ||||
| 	else if (Saltlen == -2) | ||||
| 		pad_mode = RSA_X931_PADDING; | ||||
| 	else | ||||
| 		pad_mode = RSA_PKCS1_PADDING; | ||||
| 
 | ||||
| 	if (!EVP_DigestInit_ex(&ctx, dgst, NULL)) | ||||
| 		goto error; | ||||
| 	if (!EVP_DigestUpdate(&ctx, Msg, Msglen)) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	no_err = 1; | ||||
| 	r = FIPS_rsa_verify_ctx(rsa_pubkey, &ctx, | ||||
| 				pad_mode, Saltlen, NULL, S, Slen); | ||||
| 	no_err = 0; | ||||
| 
 | ||||
| 
 | ||||
| 	EVP_MD_CTX_cleanup(&ctx); | ||||
| 
 | ||||
| 	if (r < 0) | ||||
| 		goto error; | ||||
| 
 | ||||
| 	if (r == 0) | ||||
| 		fputs("Result = F\n", out); | ||||
| 	else | ||||
| 		fputs("Result = P\n", out); | ||||
| 
 | ||||
| 	ret = 1; | ||||
| 
 | ||||
| 	error: | ||||
| 	if (rsa_pubkey) | ||||
| 		FIPS_rsa_free(rsa_pubkey); | ||||
| 	if (buf) | ||||
| 		OPENSSL_free(buf); | ||||
| 
 | ||||
| 	return ret; | ||||
| 	} | ||||
| #endif | ||||
|  | @ -0,0 +1,73 @@ | |||
| #
 | ||||
| # OpenSSL/fips/utl/Makefile
 | ||||
| #
 | ||||
| 
 | ||||
| DIR=	callback | ||||
| TOP=	../.. | ||||
| CC=	cc | ||||
| INCLUDES= | ||||
| CFLAG=-g | ||||
| INSTALL_PREFIX= | ||||
| OPENSSLDIR=     /usr/local/ssl | ||||
| INSTALLTOP=/usr/local/ssl | ||||
| MAKEDEPPROG=	makedepend | ||||
| MAKEDEPEND=	$(TOP)/util/domd $(TOP) -MD $(MAKEDEPPROG) | ||||
| MAKEFILE=	Makefile | ||||
| AR=		ar r | ||||
| 
 | ||||
| CFLAGS= $(INCLUDES) $(CFLAG) | ||||
| 
 | ||||
| GENERAL=Makefile | ||||
| TEST= | ||||
| APPS= | ||||
| 
 | ||||
| LIB=$(TOP)/libcrypto.a | ||||
| LIBSRC= fips_err.c fips_md.c fips_enc.c | ||||
| LIBOBJ= fips_err.o fips_md.o fips_enc.o | ||||
| 
 | ||||
| SRC= $(LIBSRC) | ||||
| 
 | ||||
| EXHEADER= | ||||
| HEADER=	$(EXHEADER) | ||||
| 
 | ||||
| ALL=    $(GENERAL) $(SRC) $(HEADER) | ||||
| 
 | ||||
| top: | ||||
| 	(cd $(TOP); $(MAKE) DIRS=fips FDIRS=$(DIR) sub_all) | ||||
| 
 | ||||
| all:	lib | ||||
| 
 | ||||
| lib:	$(LIBOBJ) | ||||
| 	@echo $(LIBOBJ) > lib | ||||
| 
 | ||||
| files: | ||||
| 	$(PERL) $(TOP)/util/files.pl Makefile >> $(TOP)/MINFO | ||||
| 
 | ||||
| links: | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/include/openssl $(EXHEADER) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/test $(TEST) | ||||
| 	@$(PERL) $(TOP)/util/mklink.pl $(TOP)/apps $(APPS) | ||||
| 
 | ||||
| install: | ||||
| 	@headerlist="$(EXHEADER)"; for i in $$headerlist; \
 | ||||
| 	do  \
 | ||||
| 	  (cp $$i $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i; \
 | ||||
| 	  chmod 644 $(INSTALL_PREFIX)$(INSTALLTOP)/include/openssl/$$i ); \
 | ||||
| 	done | ||||
| 
 | ||||
| tags: | ||||
| 	ctags $(SRC) | ||||
| 
 | ||||
| tests: | ||||
| 
 | ||||
| depend: | ||||
| 	$(MAKEDEPEND) -- $(CFLAG) $(INCLUDES) $(DEPFLAG) -- $(SRC) $(TEST) | ||||
| 
 | ||||
| dclean: | ||||
| 	$(PERL) -pe 'if (/^# DO NOT DELETE THIS LINE/) {print; exit(0);}' $(MAKEFILE) >Makefile.new | ||||
| 	mv -f Makefile.new $(MAKEFILE) | ||||
| 
 | ||||
| clean: | ||||
| 	rm -f *.o *.obj lib tags core .pure .nfs* *.old *.bak fluff | ||||
| # DO NOT DELETE THIS LINE -- make depend depends on it.
 | ||||
| 
 | ||||
|  | @ -0,0 +1,228 @@ | |||
| /* fipe/evp/fips_enc.c */ | ||||
| /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
 | ||||
|  * All rights reserved. | ||||
|  * | ||||
|  * This package is an SSL implementation written | ||||
|  * by Eric Young (eay@cryptsoft.com). | ||||
|  * The implementation was written so as to conform with Netscapes SSL. | ||||
|  *  | ||||
|  * This library is free for commercial and non-commercial use as long as | ||||
|  * the following conditions are aheared to.  The following conditions | ||||
|  * apply to all code found in this distribution, be it the RC4, RSA, | ||||
|  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation | ||||
|  * included with this distribution is covered by the same copyright terms | ||||
|  * except that the holder is Tim Hudson (tjh@cryptsoft.com). | ||||
|  *  | ||||
|  * Copyright remains Eric Young's, and as such any Copyright notices in | ||||
|  * the code are not to be removed. | ||||
|  * If this package is used in a product, Eric Young should be given attribution | ||||
|  * as the author of the parts of the library used. | ||||
|  * This can be in the form of a textual message at program startup or | ||||
|  * in documentation (online or textual) provided with the package. | ||||
|  *  | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * 1. Redistributions of source code must retain the copyright | ||||
|  *    notice, this list of conditions and the following disclaimer. | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in the | ||||
|  *    documentation and/or other materials provided with the distribution. | ||||
|  * 3. All advertising materials mentioning features or use of this software | ||||
|  *    must display the following acknowledgement: | ||||
|  *    "This product includes cryptographic software written by | ||||
|  *     Eric Young (eay@cryptsoft.com)" | ||||
|  *    The word 'cryptographic' can be left out if the rouines from the library | ||||
|  *    being used are not cryptographic related :-). | ||||
|  * 4. If you include any Windows specific code (or a derivative thereof) from  | ||||
|  *    the apps directory (application code) you must include an acknowledgement: | ||||
|  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | ||||
|  *  | ||||
|  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND | ||||
|  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||||
|  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | ||||
|  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||||
|  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||||
|  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||||
|  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||||
|  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||||
|  * SUCH DAMAGE. | ||||
|  *  | ||||
|  * The licence and distribution terms for any publically available version or | ||||
|  * derivative of this code cannot be changed.  i.e. this code cannot simply be | ||||
|  * copied and put under another distribution licence | ||||
|  * [including the GNU Public Licence.] | ||||
|  */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <string.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/rand.h> | ||||
| 
 | ||||
| void FIPS_cipher_ctx_init(EVP_CIPHER_CTX *ctx) | ||||
| 	{ | ||||
| 	memset(ctx,0,sizeof(EVP_CIPHER_CTX)); | ||||
| 	/* ctx->cipher=NULL; */ | ||||
| 	} | ||||
| 
 | ||||
| EVP_CIPHER_CTX *FIPS_cipher_ctx_new(void) | ||||
| 	{ | ||||
| 	EVP_CIPHER_CTX *ctx=OPENSSL_malloc(sizeof *ctx); | ||||
| 	if (ctx) | ||||
| 		FIPS_cipher_ctx_init(ctx); | ||||
| 	return ctx; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_cipherinit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher, | ||||
| 	     const unsigned char *key, const unsigned char *iv, int enc) | ||||
| 	{ | ||||
| 	if (enc == -1) | ||||
| 		enc = ctx->encrypt; | ||||
| 	else | ||||
| 		{ | ||||
| 		if (enc) | ||||
| 			enc = 1; | ||||
| 		ctx->encrypt = enc; | ||||
| 		} | ||||
| 	if (cipher) | ||||
| 		{ | ||||
| 		/* Ensure a context left lying around from last time is cleared
 | ||||
| 		 * (the previous check attempted to avoid this if the same | ||||
| 		 * ENGINE and EVP_CIPHER could be used). */ | ||||
| 		FIPS_cipher_ctx_cleanup(ctx); | ||||
| 
 | ||||
| 		/* Restore encrypt field: it is zeroed by cleanup */ | ||||
| 		ctx->encrypt = enc; | ||||
| 
 | ||||
| 		ctx->cipher=cipher; | ||||
| 		if (ctx->cipher->ctx_size) | ||||
| 			{ | ||||
| 			ctx->cipher_data=OPENSSL_malloc(ctx->cipher->ctx_size); | ||||
| 			if (!ctx->cipher_data) | ||||
| 				{ | ||||
| 				EVPerr(EVP_F_EVP_CIPHERINIT_EX, ERR_R_MALLOC_FAILURE); | ||||
| 				return 0; | ||||
| 				} | ||||
| 			} | ||||
| 		else | ||||
| 			{ | ||||
| 			ctx->cipher_data = NULL; | ||||
| 			} | ||||
| 		ctx->key_len = cipher->key_len; | ||||
| 		ctx->flags = 0; | ||||
| 		if(ctx->cipher->flags & EVP_CIPH_CTRL_INIT) | ||||
| 			{ | ||||
| 			if(!FIPS_cipher_ctx_ctrl(ctx, EVP_CTRL_INIT, 0, NULL)) | ||||
| 				{ | ||||
| 				EVPerr(EVP_F_EVP_CIPHERINIT_EX, EVP_R_INITIALIZATION_ERROR); | ||||
| 				return 0; | ||||
| 				} | ||||
| 			} | ||||
| 		} | ||||
| 	else if(!ctx->cipher) | ||||
| 		{ | ||||
| 		EVPerr(EVP_F_EVP_CIPHERINIT_EX, EVP_R_NO_CIPHER_SET); | ||||
| 		return 0; | ||||
| 		} | ||||
| 	/* we assume block size is a power of 2 in *cryptUpdate */ | ||||
| 	OPENSSL_assert(ctx->cipher->block_size == 1 | ||||
| 	    || ctx->cipher->block_size == 8 | ||||
| 	    || ctx->cipher->block_size == 16); | ||||
| 
 | ||||
| 	if(!(M_EVP_CIPHER_CTX_flags(ctx) & EVP_CIPH_CUSTOM_IV)) { | ||||
| 		switch(M_EVP_CIPHER_CTX_mode(ctx)) { | ||||
| 
 | ||||
| 			case EVP_CIPH_STREAM_CIPHER: | ||||
| 			case EVP_CIPH_ECB_MODE: | ||||
| 			break; | ||||
| 
 | ||||
| 			case EVP_CIPH_CFB_MODE: | ||||
| 			case EVP_CIPH_OFB_MODE: | ||||
| 
 | ||||
| 			ctx->num = 0; | ||||
| 			/* fall-through */ | ||||
| 
 | ||||
| 			case EVP_CIPH_CBC_MODE: | ||||
| 
 | ||||
| 			OPENSSL_assert(M_EVP_CIPHER_CTX_iv_length(ctx) <= | ||||
| 					(int)sizeof(ctx->iv)); | ||||
| 			if(iv) memcpy(ctx->oiv, iv, M_EVP_CIPHER_CTX_iv_length(ctx)); | ||||
| 			memcpy(ctx->iv, ctx->oiv, M_EVP_CIPHER_CTX_iv_length(ctx)); | ||||
| 			break; | ||||
| 
 | ||||
| 			case EVP_CIPH_CTR_MODE: | ||||
| 			/* Don't reuse IV for CTR mode */ | ||||
| 			if(iv) | ||||
| 				memcpy(ctx->iv, iv, M_EVP_CIPHER_CTX_iv_length(ctx)); | ||||
| 			break; | ||||
| 
 | ||||
| 			default: | ||||
| 			return 0; | ||||
| 			break; | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	if(key || (ctx->cipher->flags & EVP_CIPH_ALWAYS_CALL_INIT)) { | ||||
| 		if(!ctx->cipher->init(ctx,key,iv,enc)) return 0; | ||||
| 	} | ||||
| 	ctx->buf_len=0; | ||||
| 	ctx->final_used=0; | ||||
| 	ctx->block_mask=ctx->cipher->block_size-1; | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_cipher_ctx_free(EVP_CIPHER_CTX *ctx) | ||||
| 	{ | ||||
| 	if (ctx) | ||||
| 		{ | ||||
| 		FIPS_cipher_ctx_cleanup(ctx); | ||||
| 		OPENSSL_free(ctx); | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_cipher_ctx_cleanup(EVP_CIPHER_CTX *c) | ||||
| 	{ | ||||
| 	if (c->cipher != NULL) | ||||
| 		{ | ||||
| 		if(c->cipher->cleanup && !c->cipher->cleanup(c)) | ||||
| 			return 0; | ||||
| 		/* Cleanse cipher context data */ | ||||
| 		if (c->cipher_data) | ||||
| 			OPENSSL_cleanse(c->cipher_data, c->cipher->ctx_size); | ||||
| 		} | ||||
| 	if (c->cipher_data) | ||||
| 		OPENSSL_free(c->cipher_data); | ||||
| 	memset(c,0,sizeof(EVP_CIPHER_CTX)); | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_cipher_ctx_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg, void *ptr) | ||||
| { | ||||
| 	int ret; | ||||
| 	if(!ctx->cipher) { | ||||
| 		EVPerr(EVP_F_EVP_CIPHER_CTX_CTRL, EVP_R_NO_CIPHER_SET); | ||||
| 		return 0; | ||||
| 	} | ||||
| 
 | ||||
| 	if(!ctx->cipher->ctrl) { | ||||
| 		EVPerr(EVP_F_EVP_CIPHER_CTX_CTRL, EVP_R_CTRL_NOT_IMPLEMENTED); | ||||
| 		return 0; | ||||
| 	} | ||||
| 
 | ||||
| 	ret = ctx->cipher->ctrl(ctx, type, arg, ptr); | ||||
| 	if(ret == -1) { | ||||
| 		EVPerr(EVP_F_EVP_CIPHER_CTX_CTRL, EVP_R_CTRL_OPERATION_NOT_IMPLEMENTED); | ||||
| 		return 0; | ||||
| 	} | ||||
| 	return ret; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| int FIPS_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, | ||||
| 			const unsigned char *in, unsigned int inl) | ||||
| 	{ | ||||
| 	return ctx->cipher->do_cipher(ctx,out,in,inl); | ||||
| 	} | ||||
|  | @ -0,0 +1,87 @@ | |||
| /* fips/utl/fips_err.c */ | ||||
| /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 | ||||
|  * project. | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 2010 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    licensing@OpenSSL.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  */ | ||||
| 
 | ||||
| #include <openssl/err.h> | ||||
| #include <openssl/fips.h> | ||||
| 
 | ||||
| /* FIPS error callbacks */ | ||||
| 
 | ||||
| static void (*fips_put_error_cb)(int lib, int func,int reason,const char *file,int line) = 0; | ||||
| static void (*fips_add_error_vdata)(int num, va_list args) = 0; | ||||
| 
 | ||||
| void FIPS_put_error(int lib, int func,int reason,const char *file,int line) | ||||
| 	{ | ||||
| 	if (fips_put_error_cb) | ||||
| 		fips_put_error_cb(lib, func, reason, file, line); | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_add_error_data(int num, ...) | ||||
| 	{ | ||||
| 	if (fips_add_error_vdata) | ||||
| 		{ | ||||
| 		va_list args; | ||||
| 		va_start(args, num); | ||||
| 		fips_add_error_vdata(num, args); | ||||
| 		va_end(args); | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_set_error_callbacks( | ||||
| 	void (*put_cb)(int lib, int func,int reason,const char *file,int line), | ||||
| 	void (*add_cb)(int num, va_list args) ) | ||||
| 	{ | ||||
| 	fips_put_error_cb = put_cb; | ||||
| 	fips_add_error_vdata = add_cb; | ||||
| 	} | ||||
| 
 | ||||
| 
 | ||||
|  | @ -0,0 +1,265 @@ | |||
| /* fips/evp/fips_md.c */ | ||||
| /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
 | ||||
|  * All rights reserved. | ||||
|  * | ||||
|  * This package is an SSL implementation written | ||||
|  * by Eric Young (eay@cryptsoft.com). | ||||
|  * The implementation was written so as to conform with Netscapes SSL. | ||||
|  *  | ||||
|  * This library is free for commercial and non-commercial use as long as | ||||
|  * the following conditions are aheared to.  The following conditions | ||||
|  * apply to all code found in this distribution, be it the RC4, RSA, | ||||
|  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation | ||||
|  * included with this distribution is covered by the same copyright terms | ||||
|  * except that the holder is Tim Hudson (tjh@cryptsoft.com). | ||||
|  *  | ||||
|  * Copyright remains Eric Young's, and as such any Copyright notices in | ||||
|  * the code are not to be removed. | ||||
|  * If this package is used in a product, Eric Young should be given attribution | ||||
|  * as the author of the parts of the library used. | ||||
|  * This can be in the form of a textual message at program startup or | ||||
|  * in documentation (online or textual) provided with the package. | ||||
|  *  | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * 1. Redistributions of source code must retain the copyright | ||||
|  *    notice, this list of conditions and the following disclaimer. | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in the | ||||
|  *    documentation and/or other materials provided with the distribution. | ||||
|  * 3. All advertising materials mentioning features or use of this software | ||||
|  *    must display the following acknowledgement: | ||||
|  *    "This product includes cryptographic software written by | ||||
|  *     Eric Young (eay@cryptsoft.com)" | ||||
|  *    The word 'cryptographic' can be left out if the rouines from the library | ||||
|  *    being used are not cryptographic related :-). | ||||
|  * 4. If you include any Windows specific code (or a derivative thereof) from  | ||||
|  *    the apps directory (application code) you must include an acknowledgement: | ||||
|  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | ||||
|  *  | ||||
|  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND | ||||
|  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||||
|  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | ||||
|  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||||
|  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||||
|  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||||
|  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||||
|  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||||
|  * SUCH DAMAGE. | ||||
|  *  | ||||
|  * The licence and distribution terms for any publically available version or | ||||
|  * derivative of this code cannot be changed.  i.e. this code cannot simply be | ||||
|  * copied and put under another distribution licence | ||||
|  * [including the GNU Public Licence.] | ||||
|  */ | ||||
| /* ====================================================================
 | ||||
|  * Copyright (c) 1998-2001 The OpenSSL Project.  All rights reserved. | ||||
|  * | ||||
|  * Redistribution and use in source and binary forms, with or without | ||||
|  * modification, are permitted provided that the following conditions | ||||
|  * are met: | ||||
|  * | ||||
|  * 1. Redistributions of source code must retain the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer.  | ||||
|  * | ||||
|  * 2. Redistributions in binary form must reproduce the above copyright | ||||
|  *    notice, this list of conditions and the following disclaimer in | ||||
|  *    the documentation and/or other materials provided with the | ||||
|  *    distribution. | ||||
|  * | ||||
|  * 3. All advertising materials mentioning features or use of this | ||||
|  *    software must display the following acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||||
|  *    endorse or promote products derived from this software without | ||||
|  *    prior written permission. For written permission, please contact | ||||
|  *    openssl-core@openssl.org. | ||||
|  * | ||||
|  * 5. Products derived from this software may not be called "OpenSSL" | ||||
|  *    nor may "OpenSSL" appear in their names without prior written | ||||
|  *    permission of the OpenSSL Project. | ||||
|  * | ||||
|  * 6. Redistributions of any form whatsoever must retain the following | ||||
|  *    acknowledgment: | ||||
|  *    "This product includes software developed by the OpenSSL Project | ||||
|  *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
 | ||||
|  * | ||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. | ||||
|  * ==================================================================== | ||||
|  * | ||||
|  * This product includes cryptographic software written by Eric Young | ||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim | ||||
|  * Hudson (tjh@cryptsoft.com). | ||||
|  * | ||||
|  */ | ||||
| 
 | ||||
| /* Minimal standalone FIPS versions of Digest operations */ | ||||
| 
 | ||||
| #include <stdio.h> | ||||
| #include <string.h> | ||||
| #include <openssl/objects.h> | ||||
| #include <openssl/evp.h> | ||||
| #include <openssl/err.h> | ||||
| 
 | ||||
| void FIPS_md_ctx_init(EVP_MD_CTX *ctx) | ||||
| 	{ | ||||
| 	memset(ctx,'\0',sizeof *ctx); | ||||
| 	} | ||||
| 
 | ||||
| EVP_MD_CTX *FIPS_md_ctx_create(void) | ||||
| 	{ | ||||
| 	EVP_MD_CTX *ctx=OPENSSL_malloc(sizeof *ctx); | ||||
| 
 | ||||
| 	if (ctx) | ||||
| 		FIPS_md_ctx_init(ctx); | ||||
| 
 | ||||
| 	return ctx; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_digestinit(EVP_MD_CTX *ctx, const EVP_MD *type) | ||||
| 	{ | ||||
| 	M_EVP_MD_CTX_clear_flags(ctx,EVP_MD_CTX_FLAG_CLEANED); | ||||
| 	if (ctx->digest != type) | ||||
| 		{ | ||||
| 		if (ctx->digest && ctx->digest->ctx_size) | ||||
| 			OPENSSL_free(ctx->md_data); | ||||
| 		ctx->digest=type; | ||||
| 		if (!(ctx->flags & EVP_MD_CTX_FLAG_NO_INIT) && type->ctx_size) | ||||
| 			{ | ||||
| 			ctx->update = type->update; | ||||
| 			ctx->md_data=OPENSSL_malloc(type->ctx_size); | ||||
| 			if (ctx->md_data == NULL) | ||||
| 				{ | ||||
| 				EVPerr(EVP_F_EVP_DIGESTINIT_EX, | ||||
| 							ERR_R_MALLOC_FAILURE); | ||||
| 				return 0; | ||||
| 				} | ||||
| 			} | ||||
| 		} | ||||
| 	if (ctx->flags & EVP_MD_CTX_FLAG_NO_INIT) | ||||
| 		return 1; | ||||
| 	return ctx->digest->init(ctx); | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_digestupdate(EVP_MD_CTX *ctx, const void *data, size_t count) | ||||
| 	{ | ||||
| 	return ctx->update(ctx,data,count); | ||||
| 	} | ||||
| 
 | ||||
| /* The caller can assume that this removes any secret data from the context */ | ||||
| int FIPS_digestfinal(EVP_MD_CTX *ctx, unsigned char *md, unsigned int *size) | ||||
| 	{ | ||||
| 	int ret; | ||||
| 
 | ||||
| 	OPENSSL_assert(ctx->digest->md_size <= EVP_MAX_MD_SIZE); | ||||
| 	ret=ctx->digest->final(ctx,md); | ||||
| 	if (size != NULL) | ||||
| 		*size=ctx->digest->md_size; | ||||
| 	if (ctx->digest->cleanup) | ||||
| 		{ | ||||
| 		ctx->digest->cleanup(ctx); | ||||
| 		M_EVP_MD_CTX_set_flags(ctx,EVP_MD_CTX_FLAG_CLEANED); | ||||
| 		} | ||||
| 	memset(ctx->md_data,0,ctx->digest->ctx_size); | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_digest(const void *data, size_t count, | ||||
| 		unsigned char *md, unsigned int *size, const EVP_MD *type) | ||||
| 	{ | ||||
| 	EVP_MD_CTX ctx; | ||||
| 	int ret; | ||||
| 
 | ||||
| 	FIPS_md_ctx_init(&ctx); | ||||
| 	M_EVP_MD_CTX_set_flags(&ctx,EVP_MD_CTX_FLAG_ONESHOT); | ||||
| 	ret=FIPS_digestinit(&ctx, type) | ||||
| 	  && FIPS_digestupdate(&ctx, data, count) | ||||
| 	  && FIPS_digestfinal(&ctx, md, size); | ||||
| 	FIPS_md_ctx_cleanup(&ctx); | ||||
| 
 | ||||
| 	return ret; | ||||
| 	} | ||||
| 
 | ||||
| void FIPS_md_ctx_destroy(EVP_MD_CTX *ctx) | ||||
| 	{ | ||||
| 	FIPS_md_ctx_cleanup(ctx); | ||||
| 	OPENSSL_free(ctx); | ||||
| 	} | ||||
| 
 | ||||
| /* This call frees resources associated with the context */ | ||||
| int FIPS_md_ctx_cleanup(EVP_MD_CTX *ctx) | ||||
| 	{ | ||||
| 	/* Don't assume ctx->md_data was cleaned in EVP_Digest_Final,
 | ||||
| 	 * because sometimes only copies of the context are ever finalised. | ||||
| 	 */ | ||||
| 	if (ctx->digest && ctx->digest->cleanup | ||||
| 	    && !M_EVP_MD_CTX_test_flags(ctx,EVP_MD_CTX_FLAG_CLEANED)) | ||||
| 		ctx->digest->cleanup(ctx); | ||||
| 	if (ctx->digest && ctx->digest->ctx_size && ctx->md_data | ||||
| 	    && !M_EVP_MD_CTX_test_flags(ctx, EVP_MD_CTX_FLAG_REUSE)) | ||||
| 		{ | ||||
| 		OPENSSL_cleanse(ctx->md_data,ctx->digest->ctx_size); | ||||
| 		OPENSSL_free(ctx->md_data); | ||||
| 		} | ||||
| 	memset(ctx,'\0',sizeof *ctx); | ||||
| 
 | ||||
| 	return 1; | ||||
| 	} | ||||
| 
 | ||||
| int FIPS_md_ctx_copy(EVP_MD_CTX *out, const EVP_MD_CTX *in) | ||||
| 	{ | ||||
| 	unsigned char *tmp_buf; | ||||
| 	if ((in == NULL) || (in->digest == NULL)) | ||||
| 		{ | ||||
| 		EVPerr(EVP_F_EVP_MD_CTX_COPY_EX,EVP_R_INPUT_NOT_INITIALIZED); | ||||
| 		return 0; | ||||
| 		} | ||||
| 
 | ||||
| 	if (out->digest == in->digest) | ||||
| 		{ | ||||
| 		tmp_buf = out->md_data; | ||||
| 	    	M_EVP_MD_CTX_set_flags(out,EVP_MD_CTX_FLAG_REUSE); | ||||
| 		} | ||||
| 	else tmp_buf = NULL; | ||||
| 	FIPS_md_ctx_cleanup(out); | ||||
| 	memcpy(out,in,sizeof *out); | ||||
| 
 | ||||
| 	if (in->md_data && out->digest->ctx_size) | ||||
| 		{ | ||||
| 		if (tmp_buf) | ||||
| 			out->md_data = tmp_buf; | ||||
| 		else | ||||
| 			{ | ||||
| 			out->md_data=OPENSSL_malloc(out->digest->ctx_size); | ||||
| 			if (!out->md_data) | ||||
| 				{ | ||||
| 				EVPerr(EVP_F_EVP_MD_CTX_COPY_EX,ERR_R_MALLOC_FAILURE); | ||||
| 				return 0; | ||||
| 				} | ||||
| 			} | ||||
| 		memcpy(out->md_data,in->md_data,out->digest->ctx_size); | ||||
| 		} | ||||
| 
 | ||||
| 	out->update = in->update; | ||||
| 
 | ||||
| 	if (out->digest->copy) | ||||
| 		return out->digest->copy(out,in); | ||||
| 	 | ||||
| 	return 1; | ||||
| 	} | ||||
		Loading…
	
		Reference in New Issue