mirror of https://github.com/openssl/openssl.git
				
				
				
			Add a gettable for provider ciphers to return the EVP_CIPH_RAND_KEY flag
Fixes #15531 DES and TDES set this flag which could possibly be used by applications. The gettable cipher param OSSL_CIPHER_PARAM_HAS_RAND_KEY has been added. Note that EVP_CIPHER_CTX_rand_key() uses this flag. Reviewed-by: Tomas Mraz <tomas@openssl.org> Reviewed-by: Paul Dale <pauli@openssl.org> (Merged from https://github.com/openssl/openssl/pull/15606)
This commit is contained in:
		
							parent
							
								
									5135a9bd92
								
							
						
					
					
						commit
						f41fd10d90
					
				|  | @ -340,12 +340,12 @@ int EVP_CIPHER_get_type(const EVP_CIPHER *cipher) | |||
| 
 | ||||
| int evp_cipher_cache_constants(EVP_CIPHER *cipher) | ||||
| { | ||||
|     int ok, aead = 0, custom_iv = 0, cts = 0, multiblock = 0; | ||||
|     int ok, aead = 0, custom_iv = 0, cts = 0, multiblock = 0, randkey = 0; | ||||
|     size_t ivlen = 0; | ||||
|     size_t blksz = 0; | ||||
|     size_t keylen = 0; | ||||
|     unsigned int mode = 0; | ||||
|     OSSL_PARAM params[9]; | ||||
|     OSSL_PARAM params[10]; | ||||
| 
 | ||||
|     params[0] = OSSL_PARAM_construct_size_t(OSSL_CIPHER_PARAM_BLOCK_SIZE, &blksz); | ||||
|     params[1] = OSSL_PARAM_construct_size_t(OSSL_CIPHER_PARAM_IVLEN, &ivlen); | ||||
|  | @ -357,7 +357,9 @@ int evp_cipher_cache_constants(EVP_CIPHER *cipher) | |||
|     params[6] = OSSL_PARAM_construct_int(OSSL_CIPHER_PARAM_CTS, &cts); | ||||
|     params[7] = OSSL_PARAM_construct_int(OSSL_CIPHER_PARAM_TLS1_MULTIBLOCK, | ||||
|                                          &multiblock); | ||||
|     params[8] = OSSL_PARAM_construct_end(); | ||||
|     params[8] = OSSL_PARAM_construct_int(OSSL_CIPHER_PARAM_HAS_RAND_KEY, | ||||
|                                          &randkey); | ||||
|     params[9] = OSSL_PARAM_construct_end(); | ||||
|     ok = evp_do_ciph_getparams(cipher, params) > 0; | ||||
|     if (ok) { | ||||
|         cipher->block_size = blksz; | ||||
|  | @ -374,6 +376,8 @@ int evp_cipher_cache_constants(EVP_CIPHER *cipher) | |||
|             cipher->flags |= EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK; | ||||
|         if (cipher->ccipher != NULL) | ||||
|             cipher->flags |= EVP_CIPH_FLAG_CUSTOM_CIPHER; | ||||
|         if (randkey) | ||||
|             cipher->flags |= EVP_CIPH_RAND_KEY; | ||||
|         if (OSSL_PARAM_locate_const(EVP_CIPHER_gettable_ctx_params(cipher), | ||||
|                                     OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS)) | ||||
|             cipher->flags |= EVP_CIPH_FLAG_CUSTOM_ASN1; | ||||
|  |  | |||
|  | @ -679,6 +679,12 @@ TLS ciphers. | |||
| Use (EVP_CIPHER_get_flags(cipher) & EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK) to retrieve the | ||||
| cached value. | ||||
| 
 | ||||
| =item "has-randkey" (B<OSSL_CIPHER_PARAM_HAS_RANDKEY>) <integer> | ||||
| 
 | ||||
| Gets 1 if the cipher algorithm I<cipher> supports the gettable EVP_CIPHER_CTX | ||||
| parameter B<OSSL_CIPHER_PARAM_RANDOM_KEY>. Only DES and 3DES set this to 1, | ||||
| all other OpenSSL ciphers return 0. | ||||
| 
 | ||||
| =back | ||||
| 
 | ||||
| =head2 Gettable and Settable EVP_CIPHER_CTX parameters | ||||
|  | @ -1115,6 +1121,10 @@ See L</Gettable EVP_CIPHER parameters> "cts". | |||
| 
 | ||||
| See L</Gettable EVP_CIPHER parameters> "tls-multi". | ||||
| 
 | ||||
| =item EVP_CIPH_RAND_KEY | ||||
| 
 | ||||
| See L</Gettable EVP_CIPHER parameters> "has-randkey". | ||||
| 
 | ||||
| =back | ||||
| 
 | ||||
| EVP_CIPHER_flags() uses the following flags for legacy purposes only: | ||||
|  | @ -1131,8 +1141,6 @@ EVP_CIPHER_flags() uses the following flags for legacy purposes only: | |||
| 
 | ||||
| =item EVP_CIPH_CUSTOM_KEY_LENGTH | ||||
| 
 | ||||
| =item EVP_CIPH_RAND_KEY | ||||
| 
 | ||||
| =item EVP_CIPH_CUSTOM_COPY | ||||
| 
 | ||||
| =item EVP_CIPH_FLAG_DEFAULT_ASN1 | ||||
|  |  | |||
|  | @ -75,6 +75,7 @@ extern "C" { | |||
| #define OSSL_CIPHER_PARAM_CUSTOM_IV            "custom-iv"    /* int, 0 or 1 */ | ||||
| #define OSSL_CIPHER_PARAM_CTS                  "cts"          /* int, 0 or 1 */ | ||||
| #define OSSL_CIPHER_PARAM_TLS1_MULTIBLOCK      "tls-multi"    /* int, 0 or 1 */ | ||||
| #define OSSL_CIPHER_PARAM_HAS_RAND_KEY         "has-randkey"  /* int, 0 or 1 */ | ||||
| #define OSSL_CIPHER_PARAM_KEYLEN               "keylen"       /* size_t */ | ||||
| #define OSSL_CIPHER_PARAM_IVLEN                "ivlen"        /* size_t */ | ||||
| #define OSSL_CIPHER_PARAM_IV                   "iv"           /* octet_string OR octet_ptr */ | ||||
|  |  | |||
|  | @ -20,7 +20,7 @@ | |||
| #include "prov/implementations.h" | ||||
| #include "prov/providercommon.h" | ||||
| 
 | ||||
| #define DES_FLAGS 0 | ||||
| #define DES_FLAGS PROV_CIPHER_FLAG_RAND_KEY | ||||
| 
 | ||||
| static OSSL_FUNC_cipher_freectx_fn des_freectx; | ||||
| static OSSL_FUNC_cipher_encrypt_init_fn des_einit; | ||||
|  |  | |||
|  | @ -13,7 +13,7 @@ | |||
| 
 | ||||
| #define DES_BLOCK_SIZE 8 | ||||
| #define TDES_IVLEN 8 | ||||
| #define TDES_FLAGS 0 | ||||
| #define TDES_FLAGS PROV_CIPHER_FLAG_RAND_KEY | ||||
| 
 | ||||
| typedef struct prov_tdes_ctx_st { | ||||
|     PROV_CIPHER_CTX base;      /* Must be first */ | ||||
|  |  | |||
|  | @ -22,7 +22,7 @@ | |||
| #include "prov/implementations.h" | ||||
| #include "prov/providercommon.h" | ||||
| 
 | ||||
| #define TDES_WRAP_FLAGS PROV_CIPHER_FLAG_CUSTOM_IV | ||||
| #define TDES_WRAP_FLAGS PROV_CIPHER_FLAG_CUSTOM_IV | PROV_CIPHER_FLAG_RAND_KEY | ||||
| 
 | ||||
| static OSSL_FUNC_cipher_update_fn tdes_wrap_update; | ||||
| static OSSL_FUNC_cipher_cipher_fn tdes_wrap_cipher; | ||||
|  |  | |||
|  | @ -30,6 +30,7 @@ static const OSSL_PARAM cipher_known_gettable_params[] = { | |||
|     OSSL_PARAM_int(OSSL_CIPHER_PARAM_CUSTOM_IV, NULL), | ||||
|     OSSL_PARAM_int(OSSL_CIPHER_PARAM_CTS, NULL), | ||||
|     OSSL_PARAM_int(OSSL_CIPHER_PARAM_TLS1_MULTIBLOCK, NULL), | ||||
|     OSSL_PARAM_int(OSSL_CIPHER_PARAM_HAS_RAND_KEY, NULL), | ||||
|     OSSL_PARAM_END | ||||
| }; | ||||
| const OSSL_PARAM *ossl_cipher_generic_gettable_params(ossl_unused void *provctx) | ||||
|  | @ -72,6 +73,12 @@ int ossl_cipher_generic_get_params(OSSL_PARAM params[], unsigned int md, | |||
|         ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); | ||||
|         return 0; | ||||
|     } | ||||
|     p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_HAS_RAND_KEY); | ||||
|     if (p != NULL | ||||
|         && !OSSL_PARAM_set_int(p, (flags & PROV_CIPHER_FLAG_RAND_KEY) != 0)) { | ||||
|         ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); | ||||
|         return 0; | ||||
|     } | ||||
|     p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_KEYLEN); | ||||
|     if (p != NULL && !OSSL_PARAM_set_size_t(p, kbits / 8)) { | ||||
|         ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); | ||||
|  |  | |||
|  | @ -36,9 +36,10 @@ typedef int (PROV_CIPHER_HW_FN)(PROV_CIPHER_CTX *dat, unsigned char *out, | |||
| #define PROV_CIPHER_FLAG_CUSTOM_IV        0x0002 | ||||
| #define PROV_CIPHER_FLAG_CTS              0x0004 | ||||
| #define PROV_CIPHER_FLAG_TLS1_MULTIBLOCK  0x0008 | ||||
| #define PROV_CIPHER_FLAG_RAND_KEY         0x0010 | ||||
| /* Internal flags that are only used within the provider */ | ||||
| #define PROV_CIPHER_FLAG_VARIABLE_LENGTH  0x0010 | ||||
| #define PROV_CIPHER_FLAG_INVERSE_CIPHER   0x0020 | ||||
| #define PROV_CIPHER_FLAG_VARIABLE_LENGTH  0x0100 | ||||
| #define PROV_CIPHER_FLAG_INVERSE_CIPHER   0x0200 | ||||
| 
 | ||||
| struct prov_cipher_ctx_st { | ||||
|     block128_f block; | ||||
|  |  | |||
|  | @ -557,6 +557,33 @@ static int kem_rsa_gen_recover(void) | |||
|     return ret; | ||||
| } | ||||
| 
 | ||||
| #ifndef OPENSSL_NO_DES | ||||
| /*
 | ||||
|  * This test makes sure that EVP_CIPHER_CTX_rand_key() works correctly | ||||
|  * For fips mode this code would produce an error if the flag is not set. | ||||
|  */ | ||||
| static int test_cipher_tdes_randkey(void) | ||||
| { | ||||
|     int ret; | ||||
|     EVP_CIPHER_CTX *ctx = NULL; | ||||
|     EVP_CIPHER *tdes_cipher = NULL, *aes_cipher = NULL; | ||||
|     unsigned char key[24] = { 0 }; | ||||
| 
 | ||||
|     ret = TEST_ptr(aes_cipher = EVP_CIPHER_fetch(libctx, "AES-256-CBC", NULL)) | ||||
|           && TEST_int_eq(EVP_CIPHER_get_flags(aes_cipher) & EVP_CIPH_RAND_KEY, 0) | ||||
|           && TEST_ptr(tdes_cipher = EVP_CIPHER_fetch(libctx, "DES-EDE3-CBC", NULL)) | ||||
|           && TEST_int_ne(EVP_CIPHER_get_flags(tdes_cipher) & EVP_CIPH_RAND_KEY, 0) | ||||
|           && TEST_ptr(ctx = EVP_CIPHER_CTX_new()) | ||||
|           && TEST_true(EVP_CipherInit_ex(ctx, tdes_cipher, NULL, NULL, NULL, 1)) | ||||
|           && TEST_true(EVP_CIPHER_CTX_rand_key(ctx, key)); | ||||
| 
 | ||||
|     EVP_CIPHER_CTX_free(ctx); | ||||
|     EVP_CIPHER_free(tdes_cipher); | ||||
|     EVP_CIPHER_free(aes_cipher); | ||||
|     return ret; | ||||
| } | ||||
| #endif /* OPENSSL_NO_DES */ | ||||
| 
 | ||||
| static int kem_rsa_params(void) | ||||
| { | ||||
|     int ret = 0; | ||||
|  | @ -716,6 +743,9 @@ int setup_tests(void) | |||
|     ADD_TEST(kem_rsa_params); | ||||
| #ifndef OPENSSL_NO_DH | ||||
|     ADD_TEST(kem_invalid_keytype); | ||||
| #endif | ||||
| #ifndef OPENSSL_NO_DES | ||||
|     ADD_TEST(test_cipher_tdes_randkey); | ||||
| #endif | ||||
|     return 1; | ||||
| } | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue