2 * Copyright 2019 The OpenSSL Project Authors. All Rights Reserved.
4 * Licensed under the Apache License 2.0 (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
12 #include <openssl/core.h>
13 #include <openssl/core_numbers.h>
14 #include <openssl/core_names.h>
15 #include <openssl/params.h>
16 #include <openssl/err.h>
17 #include <openssl/evp.h>
19 /* TODO(3.0): Needed for dummy_evp_call(). To be removed */
20 #include <openssl/sha.h>
21 #include <openssl/rand_drbg.h>
22 #include <openssl/ec.h>
24 #include "internal/cryptlib.h"
25 #include "internal/property.h"
26 #include "internal/evp_int.h"
27 #include "internal/provider_algs.h"
28 #include "internal/provider_ctx.h"
29 #include "internal/providercommon.h"
31 extern OSSL_core_thread_start_fn
*c_thread_start
;
34 * TODO(3.0): Should these be stored in the provider side provctx? Could they
35 * ever be different from one init to the next? Unfortunately we can't do this
36 * at the moment because c_put_error/c_add_error_vdata do not provide
37 * us with the OPENSSL_CTX as a parameter.
39 /* Functions provided by the core */
40 static OSSL_core_gettable_params_fn
*c_gettable_params
;
41 static OSSL_core_get_params_fn
*c_get_params
;
42 OSSL_core_thread_start_fn
*c_thread_start
;
43 static OSSL_core_new_error_fn
*c_new_error
;
44 static OSSL_core_set_error_debug_fn
*c_set_error_debug
;
45 static OSSL_core_vset_error_fn
*c_vset_error
;
46 static OSSL_CRYPTO_malloc_fn
*c_CRYPTO_malloc
;
47 static OSSL_CRYPTO_zalloc_fn
*c_CRYPTO_zalloc
;
48 static OSSL_CRYPTO_free_fn
*c_CRYPTO_free
;
49 static OSSL_CRYPTO_clear_free_fn
*c_CRYPTO_clear_free
;
50 static OSSL_CRYPTO_realloc_fn
*c_CRYPTO_realloc
;
51 static OSSL_CRYPTO_clear_realloc_fn
*c_CRYPTO_clear_realloc
;
52 static OSSL_CRYPTO_secure_malloc_fn
*c_CRYPTO_secure_malloc
;
53 static OSSL_CRYPTO_secure_zalloc_fn
*c_CRYPTO_secure_zalloc
;
54 static OSSL_CRYPTO_secure_free_fn
*c_CRYPTO_secure_free
;
55 static OSSL_CRYPTO_secure_clear_free_fn
*c_CRYPTO_secure_clear_free
;
56 static OSSL_CRYPTO_secure_allocated_fn
*c_CRYPTO_secure_allocated
;
58 typedef struct fips_global_st
{
59 const OSSL_PROVIDER
*prov
;
62 static void *fips_prov_ossl_ctx_new(OPENSSL_CTX
*libctx
)
64 FIPS_GLOBAL
*fgbl
= OPENSSL_zalloc(sizeof(*fgbl
));
69 static void fips_prov_ossl_ctx_free(void *fgbl
)
74 static const OPENSSL_CTX_METHOD fips_prov_ossl_ctx_method
= {
75 fips_prov_ossl_ctx_new
,
76 fips_prov_ossl_ctx_free
,
80 /* Parameters we provide to the core */
81 static const OSSL_PARAM fips_param_types
[] = {
82 OSSL_PARAM_DEFN(OSSL_PROV_PARAM_NAME
, OSSL_PARAM_UTF8_PTR
, NULL
, 0),
83 OSSL_PARAM_DEFN(OSSL_PROV_PARAM_VERSION
, OSSL_PARAM_UTF8_PTR
, NULL
, 0),
84 OSSL_PARAM_DEFN(OSSL_PROV_PARAM_BUILDINFO
, OSSL_PARAM_UTF8_PTR
, NULL
, 0),
88 /* TODO(3.0): To be removed */
89 static int dummy_evp_call(void *provctx
)
91 OPENSSL_CTX
*libctx
= PROV_LIBRARY_CONTEXT_OF(provctx
);
92 EVP_MD_CTX
*ctx
= EVP_MD_CTX_new();
93 EVP_MD
*sha256
= EVP_MD_fetch(libctx
, "SHA256", NULL
);
94 char msg
[] = "Hello World!";
95 const unsigned char exptd
[] = {
96 0x7f, 0x83, 0xb1, 0x65, 0x7f, 0xf1, 0xfc, 0x53, 0xb9, 0x2d, 0xc1, 0x81,
97 0x48, 0xa1, 0xd6, 0x5d, 0xfc, 0x2d, 0x4b, 0x1f, 0xa3, 0xd6, 0x77, 0x28,
98 0x4a, 0xdd, 0xd2, 0x00, 0x12, 0x6d, 0x90, 0x69
100 unsigned int dgstlen
= 0;
101 unsigned char dgst
[SHA256_DIGEST_LENGTH
];
103 BN_CTX
*bnctx
= NULL
;
104 BIGNUM
*a
= NULL
, *b
= NULL
;
105 unsigned char randbuf
[128];
106 RAND_DRBG
*drbg
= OPENSSL_CTX_get0_public_drbg(libctx
);
107 #ifndef OPENSSL_NO_EC
111 if (ctx
== NULL
|| sha256
== NULL
|| drbg
== NULL
)
114 if (!EVP_DigestInit_ex(ctx
, sha256
, NULL
))
116 if (!EVP_DigestUpdate(ctx
, msg
, sizeof(msg
) - 1))
118 if (!EVP_DigestFinal(ctx
, dgst
, &dgstlen
))
120 if (dgstlen
!= sizeof(exptd
) || memcmp(dgst
, exptd
, sizeof(exptd
)) != 0)
123 bnctx
= BN_CTX_new_ex(libctx
);
127 a
= BN_CTX_get(bnctx
);
128 b
= BN_CTX_get(bnctx
);
134 || BN_cmp(a
, b
) != 0)
137 if (RAND_DRBG_bytes(drbg
, randbuf
, sizeof(randbuf
)) <= 0)
140 if (!BN_rand_ex(a
, 256, BN_RAND_TOP_ANY
, BN_RAND_BOTTOM_ANY
, bnctx
))
143 #ifndef OPENSSL_NO_EC
144 /* Do some dummy EC calls */
145 key
= EC_KEY_new_by_curve_name_ex(libctx
, NID_X9_62_prime256v1
);
149 if (!EC_KEY_generate_key(key
))
158 EVP_MD_CTX_free(ctx
);
159 EVP_MD_meth_free(sha256
);
161 #ifndef OPENSSL_NO_EC
167 static const OSSL_PARAM
*fips_gettable_params(const OSSL_PROVIDER
*prov
)
169 return fips_param_types
;
172 static int fips_get_params(const OSSL_PROVIDER
*prov
, OSSL_PARAM params
[])
176 p
= OSSL_PARAM_locate(params
, OSSL_PROV_PARAM_NAME
);
177 if (p
!= NULL
&& !OSSL_PARAM_set_utf8_ptr(p
, "OpenSSL FIPS Provider"))
179 p
= OSSL_PARAM_locate(params
, OSSL_PROV_PARAM_VERSION
);
180 if (p
!= NULL
&& !OSSL_PARAM_set_utf8_ptr(p
, OPENSSL_VERSION_STR
))
182 p
= OSSL_PARAM_locate(params
, OSSL_PROV_PARAM_BUILDINFO
);
183 if (p
!= NULL
&& !OSSL_PARAM_set_utf8_ptr(p
, OPENSSL_FULL_VERSION_STR
))
189 /* FIPS specific version of the function of the same name in provlib.c */
190 const char *ossl_prov_util_nid_to_name(int nid
)
192 /* We don't have OBJ_nid2n() in FIPS_MODE so we have an explicit list */
220 case NID_aes_256_ecb
:
221 return "AES-256-ECB";
222 case NID_aes_192_ecb
:
223 return "AES-192-ECB";
224 case NID_aes_128_ecb
:
225 return "AES-128-ECB";
226 case NID_aes_256_cbc
:
227 return "AES-256-CBC";
228 case NID_aes_192_cbc
:
229 return "AES-192-CBC";
230 case NID_aes_128_cbc
:
231 return "AES-128-CBC";
232 case NID_aes_256_ctr
:
233 return "AES-256-CTR";
234 case NID_aes_192_ctr
:
235 return "AES-192-CTR";
236 case NID_aes_128_ctr
:
237 return "AES-128-CTR";
243 static const OSSL_ALGORITHM fips_digests
[] = {
244 { "SHA1", "fips=yes", sha1_functions
},
245 { "SHA224", "fips=yes", sha224_functions
},
246 { "SHA256", "fips=yes", sha256_functions
},
247 { "SHA384", "fips=yes", sha384_functions
},
248 { "SHA512", "fips=yes", sha512_functions
},
249 { "SHA512-224", "fips=yes", sha512_224_functions
},
250 { "SHA512-256", "fips=yes", sha512_256_functions
},
251 { "SHA3-224", "fips=yes", sha3_224_functions
},
252 { "SHA3-256", "fips=yes", sha3_256_functions
},
253 { "SHA3-384", "fips=yes", sha3_384_functions
},
254 { "SHA3-512", "fips=yes", sha3_512_functions
},
255 { "KMAC128", "fips=yes", keccak_kmac_128_functions
},
256 { "KMAC256", "fips=yes", keccak_kmac_256_functions
},
261 static const OSSL_ALGORITHM fips_ciphers
[] = {
262 { "AES-256-ECB", "fips=yes", aes256ecb_functions
},
263 { "AES-192-ECB", "fips=yes", aes192ecb_functions
},
264 { "AES-128-ECB", "fips=yes", aes128ecb_functions
},
265 { "AES-256-CBC", "fips=yes", aes256cbc_functions
},
266 { "AES-192-CBC", "fips=yes", aes192cbc_functions
},
267 { "AES-128-CBC", "fips=yes", aes128cbc_functions
},
268 { "AES-256-CTR", "fips=yes", aes256ctr_functions
},
269 { "AES-192-CTR", "fips=yes", aes192ctr_functions
},
270 { "AES-128-CTR", "fips=yes", aes128ctr_functions
},
271 { "id-aes256-GCM", "fips=yes", aes256gcm_functions
},
272 { "id-aes192-GCM", "fips=yes", aes192gcm_functions
},
273 { "id-aes128-GCM", "fips=yes", aes128gcm_functions
},
277 static const OSSL_ALGORITHM fips_macs
[] = {
278 { "CMAC", "fips=yes", cmac_functions
},
279 { "GMAC", "fips=yes", gmac_functions
},
280 { "HMAC", "fips=yes", hmac_functions
},
284 static const OSSL_ALGORITHM
*fips_query(OSSL_PROVIDER
*prov
,
289 switch (operation_id
) {
300 /* Functions we provide to the core */
301 static const OSSL_DISPATCH fips_dispatch_table
[] = {
303 * To release our resources we just need to free the OPENSSL_CTX so we just
304 * use OPENSSL_CTX_free directly as our teardown function
306 { OSSL_FUNC_PROVIDER_TEARDOWN
, (void (*)(void))OPENSSL_CTX_free
},
307 { OSSL_FUNC_PROVIDER_GETTABLE_PARAMS
, (void (*)(void))fips_gettable_params
},
308 { OSSL_FUNC_PROVIDER_GET_PARAMS
, (void (*)(void))fips_get_params
},
309 { OSSL_FUNC_PROVIDER_QUERY_OPERATION
, (void (*)(void))fips_query
},
313 /* Functions we provide to ourself */
314 static const OSSL_DISPATCH intern_dispatch_table
[] = {
315 { OSSL_FUNC_PROVIDER_QUERY_OPERATION
, (void (*)(void))fips_query
},
320 int OSSL_provider_init(const OSSL_PROVIDER
*provider
,
321 const OSSL_DISPATCH
*in
,
322 const OSSL_DISPATCH
**out
,
328 for (; in
->function_id
!= 0; in
++) {
329 switch (in
->function_id
) {
330 case OSSL_FUNC_CORE_GETTABLE_PARAMS
:
331 c_gettable_params
= OSSL_get_core_gettable_params(in
);
333 case OSSL_FUNC_CORE_GET_PARAMS
:
334 c_get_params
= OSSL_get_core_get_params(in
);
336 case OSSL_FUNC_CORE_THREAD_START
:
337 c_thread_start
= OSSL_get_core_thread_start(in
);
339 case OSSL_FUNC_CORE_NEW_ERROR
:
340 c_new_error
= OSSL_get_core_new_error(in
);
342 case OSSL_FUNC_CORE_SET_ERROR_DEBUG
:
343 c_set_error_debug
= OSSL_get_core_set_error_debug(in
);
345 case OSSL_FUNC_CORE_VSET_ERROR
:
346 c_vset_error
= OSSL_get_core_vset_error(in
);
348 case OSSL_FUNC_CRYPTO_MALLOC
:
349 c_CRYPTO_malloc
= OSSL_get_CRYPTO_malloc(in
);
351 case OSSL_FUNC_CRYPTO_ZALLOC
:
352 c_CRYPTO_zalloc
= OSSL_get_CRYPTO_zalloc(in
);
354 case OSSL_FUNC_CRYPTO_FREE
:
355 c_CRYPTO_free
= OSSL_get_CRYPTO_free(in
);
357 case OSSL_FUNC_CRYPTO_CLEAR_FREE
:
358 c_CRYPTO_clear_free
= OSSL_get_CRYPTO_clear_free(in
);
360 case OSSL_FUNC_CRYPTO_REALLOC
:
361 c_CRYPTO_realloc
= OSSL_get_CRYPTO_realloc(in
);
363 case OSSL_FUNC_CRYPTO_CLEAR_REALLOC
:
364 c_CRYPTO_clear_realloc
= OSSL_get_CRYPTO_clear_realloc(in
);
366 case OSSL_FUNC_CRYPTO_SECURE_MALLOC
:
367 c_CRYPTO_secure_malloc
= OSSL_get_CRYPTO_secure_malloc(in
);
369 case OSSL_FUNC_CRYPTO_SECURE_ZALLOC
:
370 c_CRYPTO_secure_zalloc
= OSSL_get_CRYPTO_secure_zalloc(in
);
372 case OSSL_FUNC_CRYPTO_SECURE_FREE
:
373 c_CRYPTO_secure_free
= OSSL_get_CRYPTO_secure_free(in
);
375 case OSSL_FUNC_CRYPTO_SECURE_CLEAR_FREE
:
376 c_CRYPTO_secure_clear_free
= OSSL_get_CRYPTO_secure_clear_free(in
);
378 case OSSL_FUNC_CRYPTO_SECURE_ALLOCATED
:
379 c_CRYPTO_secure_allocated
= OSSL_get_CRYPTO_secure_allocated(in
);
382 /* Just ignore anything we don't understand */
387 /* Create a context. */
388 if ((ctx
= OPENSSL_CTX_new()) == NULL
)
390 if ((fgbl
= openssl_ctx_get_data(ctx
, OPENSSL_CTX_FIPS_PROV_INDEX
,
391 &fips_prov_ossl_ctx_method
)) == NULL
) {
392 OPENSSL_CTX_free(ctx
);
395 fgbl
->prov
= provider
;
396 *out
= fips_dispatch_table
;
400 * TODO(3.0): Remove me. This is just a dummy call to demonstrate making
401 * EVP calls from within the FIPS module.
403 if (!dummy_evp_call(*provctx
)) {
404 OPENSSL_CTX_free(*provctx
);
413 * The internal init function used when the FIPS module uses EVP to call
414 * another algorithm also in the FIPS module. This is a recursive call that has
415 * been made from within the FIPS module itself. To make this work, we populate
416 * the provider context of this inner instance with the same library context
417 * that was used in the EVP call that initiated this recursive call.
419 OSSL_provider_init_fn fips_intern_provider_init
;
420 int fips_intern_provider_init(const OSSL_PROVIDER
*provider
,
421 const OSSL_DISPATCH
*in
,
422 const OSSL_DISPATCH
**out
,
425 OSSL_core_get_library_context_fn
*c_get_libctx
= NULL
;
427 for (; in
->function_id
!= 0; in
++) {
428 switch (in
->function_id
) {
429 case OSSL_FUNC_CORE_GET_LIBRARY_CONTEXT
:
430 c_get_libctx
= OSSL_get_core_get_library_context(in
);
437 if (c_get_libctx
== NULL
)
440 *provctx
= c_get_libctx(provider
);
443 * Safety measure... we should get the library context that was
444 * created up in OSSL_provider_init().
446 if (*provctx
== NULL
)
449 *out
= intern_dispatch_table
;
458 void ERR_set_debug(const char *file
, int line
, const char *func
)
460 c_set_error_debug(NULL
, file
, line
, func
);
463 void ERR_set_error(int lib
, int reason
, const char *fmt
, ...)
468 c_vset_error(NULL
, ERR_PACK(lib
, 0, reason
), fmt
, args
);
472 void ERR_vset_error(int lib
, int reason
, const char *fmt
, va_list args
)
474 c_vset_error(NULL
, ERR_PACK(lib
, 0, reason
), fmt
, args
);
477 const OSSL_PROVIDER
*FIPS_get_provider(OPENSSL_CTX
*ctx
)
479 FIPS_GLOBAL
*fgbl
= openssl_ctx_get_data(ctx
, OPENSSL_CTX_FIPS_PROV_INDEX
,
480 &fips_prov_ossl_ctx_method
);
488 void *CRYPTO_malloc(size_t num
, const char *file
, int line
)
490 return c_CRYPTO_malloc(num
, file
, line
);
493 void *CRYPTO_zalloc(size_t num
, const char *file
, int line
)
495 return c_CRYPTO_zalloc(num
, file
, line
);
498 void CRYPTO_free(void *ptr
, const char *file
, int line
)
500 c_CRYPTO_free(ptr
, file
, line
);
503 void CRYPTO_clear_free(void *ptr
, size_t num
, const char *file
, int line
)
505 c_CRYPTO_clear_free(ptr
, num
, file
, line
);
508 void *CRYPTO_realloc(void *addr
, size_t num
, const char *file
, int line
)
510 return c_CRYPTO_realloc(addr
, num
, file
, line
);
513 void *CRYPTO_clear_realloc(void *addr
, size_t old_num
, size_t num
,
514 const char *file
, int line
)
516 return c_CRYPTO_clear_realloc(addr
, old_num
, num
, file
, line
);
519 void *CRYPTO_secure_malloc(size_t num
, const char *file
, int line
)
521 return c_CRYPTO_secure_malloc(num
, file
, line
);
524 void *CRYPTO_secure_zalloc(size_t num
, const char *file
, int line
)
526 return c_CRYPTO_secure_zalloc(num
, file
, line
);
529 void CRYPTO_secure_free(void *ptr
, const char *file
, int line
)
531 c_CRYPTO_secure_free(ptr
, file
, line
);
534 void CRYPTO_secure_clear_free(void *ptr
, size_t num
, const char *file
, int line
)
536 c_CRYPTO_secure_clear_free(ptr
, num
, file
, line
);
539 int CRYPTO_secure_allocated(const void *ptr
)
541 return c_CRYPTO_secure_allocated(ptr
);