diff --git a/apps/openssl.c b/apps/openssl.c index 4a6185b1e..e9c24d057 100644 --- a/apps/openssl.c +++ b/apps/openssl.c @@ -172,8 +172,9 @@ static int apps_startup() #endif /* Set non-default library initialisation settings */ - OPENSSL_init_crypto(OPENSSL_INIT_ENGINE_ALL_BUILTIN - | OPENSSL_INIT_LOAD_CONFIG, NULL); + if (!OPENSSL_init_crypto(OPENSSL_INIT_ENGINE_ALL_BUILTIN + | OPENSSL_INIT_LOAD_CONFIG, NULL)) + return 0; setup_ui_method(); diff --git a/crypto/async/async.c b/crypto/async/async.c index db511442b..af9da35f9 100644 --- a/crypto/async/async.c +++ b/crypto/async/async.c @@ -97,7 +97,8 @@ err: static async_ctx *async_get_ctx(void) { - OPENSSL_init_crypto(OPENSSL_INIT_ASYNC, NULL); + if (!OPENSSL_init_crypto(OPENSSL_INIT_ASYNC, NULL)) + return NULL; return async_arch_get_ctx(); } @@ -361,9 +362,12 @@ int ASYNC_init_thread(size_t max_size, size_t init_size) return 0; } - OPENSSL_init_crypto(OPENSSL_INIT_ASYNC, NULL); + if (!OPENSSL_init_crypto(OPENSSL_INIT_ASYNC, NULL)) { + ASYNCerr(ASYNC_F_ASYNC_INIT_THREAD, ERR_R_NOT_INITED); + return 0; + } if (!ossl_init_thread_start(OPENSSL_INIT_THREAD_ASYNC)) { - ASYNCerr(ASYNC_F_ASYNC_INIT_THREAD, ERR_R_MALLOC_FAILURE); + ASYNCerr(ASYNC_F_ASYNC_INIT_THREAD, ERR_R_NOT_INITED); return 0; } diff --git a/crypto/comp/c_zlib.c b/crypto/comp/c_zlib.c index 619765cef..baad9c66e 100644 --- a/crypto/comp/c_zlib.c +++ b/crypto/comp/c_zlib.c @@ -289,9 +289,13 @@ COMP_METHOD *COMP_zlib(void) && p_inflateInit_ && p_deflateEnd && p_deflate && p_deflateInit_ && p_zError) zlib_loaded++; + + if (!OPENSSL_init_crypto(OPENSSL_INIT_ZLIB, NULL)) { + COMP_zlib_cleanup(); + return meth; + } if (zlib_loaded) meth = &zlib_stateful_method; - OPENSSL_init_crypto(OPENSSL_INIT_ZLIB, NULL); } } #endif diff --git a/crypto/err/err.c b/crypto/err/err.c index d92e41e3e..72656339c 100644 --- a/crypto/err/err.c +++ b/crypto/err/err.c @@ -894,8 +894,9 @@ ERR_STATE *ERR_get_state(void) * the first one that we just replaced. */ ERR_STATE_free(tmpp); + + /* Ignore failures from these */ OPENSSL_init_crypto(OPENSSL_INIT_LOAD_CRYPTO_STRINGS, NULL); - /* Ignore failures from this */ ossl_init_thread_start(OPENSSL_INIT_THREAD_ERR_STATE); } return ret; diff --git a/crypto/evp/names.c b/crypto/evp/names.c index f6e500447..2a5606b04 100644 --- a/crypto/evp/names.c +++ b/crypto/evp/names.c @@ -110,7 +110,8 @@ const EVP_CIPHER *EVP_get_cipherbyname(const char *name) { const EVP_CIPHER *cp; - OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_CIPHERS, NULL); + if (!OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_CIPHERS, NULL)) + return NULL; cp = (const EVP_CIPHER *)OBJ_NAME_get(name, OBJ_NAME_TYPE_CIPHER_METH); return (cp); @@ -120,7 +121,8 @@ const EVP_MD *EVP_get_digestbyname(const char *name) { const EVP_MD *cp; - OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_DIGESTS, NULL); + if (!OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_DIGESTS, NULL)) + return NULL; cp = (const EVP_MD *)OBJ_NAME_get(name, OBJ_NAME_TYPE_MD_METH); return (cp); @@ -166,6 +168,7 @@ void EVP_CIPHER_do_all(void (*fn) (const EVP_CIPHER *ciph, { struct doall_cipher dc; + /* Ignore errors */ OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_CIPHERS, NULL); dc.fn = fn; @@ -179,6 +182,7 @@ void EVP_CIPHER_do_all_sorted(void (*fn) (const EVP_CIPHER *ciph, { struct doall_cipher dc; + /* Ignore errors */ OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_CIPHERS, NULL); dc.fn = fn; @@ -207,6 +211,7 @@ void EVP_MD_do_all(void (*fn) (const EVP_MD *md, { struct doall_md dc; + /* Ignore errors */ OPENSSL_init_crypto(OPENSSL_INIT_ADD_ALL_DIGESTS, NULL); dc.fn = fn; diff --git a/crypto/init.c b/crypto/init.c index 3238b8002..f01bd4d93 100644 --- a/crypto/init.c +++ b/crypto/init.c @@ -626,10 +626,10 @@ static const OPENSSL_INIT_SETTINGS *ossl_init_get_setting( * called prior to any threads making calls to any OpenSSL functions, * i.e. passing a non-null settings value is assumed to be single-threaded. */ -void OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) +int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) { - /* XXX TODO WARNING To be updated to return a value not assert. */ - assert(!stopped); + if (stopped) + return 0; ossl_init_once_run(&base, ossl_init_base); @@ -716,6 +716,8 @@ void OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) if (opts & OPENSSL_INIT_ZLIB) { ossl_init_once_run(&zlib, ossl_init_zlib); } + + return 1; } int OPENSSL_atexit(void (*handler)(void)) diff --git a/doc/crypto/OPENSSL_init_crypto.pod b/doc/crypto/OPENSSL_init_crypto.pod index 11bc1c7f7..67c84913c 100644 --- a/doc/crypto/OPENSSL_init_crypto.pod +++ b/doc/crypto/OPENSSL_init_crypto.pod @@ -11,7 +11,7 @@ initialisation and deinitialisation functions #include void OPENSSL_cleanup(void); - void OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); + int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); int OPENSSL_atexit(void (*handler)(void)); void OPENSSL_thread_stop(void); @@ -206,8 +206,8 @@ using static linking should also call OPENSSL_thread_stop(). =head1 RETURN VALUES -The function OPENSSL_atexit() returns 1 on success or 0 on -error. +The functions OPENSSL_init_crypto and OPENSSL_atexit() returns 1 on success or +0 on error. =head1 SEE ALSO diff --git a/doc/ssl/OPENSSL_init_ssl.pod b/doc/ssl/OPENSSL_init_ssl.pod index d9246a53c..113e93f94 100644 --- a/doc/ssl/OPENSSL_init_ssl.pod +++ b/doc/ssl/OPENSSL_init_ssl.pod @@ -8,7 +8,7 @@ OPENSSL_init_ssl - OpenSSL (libssl and libcrypto) initialisation #include - void OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); + int OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); =head1 DESCRIPTION @@ -63,6 +63,10 @@ these settings will also be passed internally to a call to L, so this parameter can also be used to provide libcrypto settings values. +=head1 RETURN VALUES + +The function OPENSSL_init_ssl() returns 1 on success or 0 on error. + =head1 SEE ALSO L diff --git a/include/openssl/crypto.h b/include/openssl/crypto.h index 16b7fbdfa..d6cedecd6 100644 --- a/include/openssl/crypto.h +++ b/include/openssl/crypto.h @@ -598,7 +598,7 @@ typedef struct ossl_init_stop_st OPENSSL_INIT_STOP; /* Library initialisation functions */ void OPENSSL_cleanup(void); -void OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); +int OPENSSL_init_crypto(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); int OPENSSL_atexit(void (*handler)(void)); void OPENSSL_thread_stop(void); diff --git a/include/openssl/err.h b/include/openssl/err.h index 147d4da72..39f216c21 100644 --- a/include/openssl/err.h +++ b/include/openssl/err.h @@ -309,6 +309,7 @@ typedef struct err_state_st { # define ERR_R_PASSED_NULL_PARAMETER (3|ERR_R_FATAL) # define ERR_R_INTERNAL_ERROR (4|ERR_R_FATAL) # define ERR_R_DISABLED (5|ERR_R_FATAL) +# define ERR_R_NOT_INITED (6|ERR_R_FATAL) /* * 99 is the maximum possible ERR_R_... code, higher values are reserved for diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h index d65ee9f70..888f9a9c9 100644 --- a/include/openssl/ssl.h +++ b/include/openssl/ssl.h @@ -1940,7 +1940,7 @@ __owur void *SSL_CTX_get0_security_ex_data(const SSL_CTX *ctx); #define OPENSSL_INIT_SSL_DEFAULT \ (OPENSSL_INIT_LOAD_SSL_STRINGS | OPENSSL_INIT_LOAD_CRYPTO_STRINGS) -void OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); +int OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings); # ifndef OPENSSL_NO_UNIT_TEST __owur const struct openssl_ssl_test_functions *SSL_test_functions(void); diff --git a/ssl/ssl_init.c b/ssl/ssl_init.c index 67e431941..134aa00d5 100644 --- a/ssl/ssl_init.c +++ b/ssl/ssl_init.c @@ -299,13 +299,14 @@ static void ssl_library_stop(void) * called prior to any threads making calls to any OpenSSL functions, * i.e. passing a non-null settings value is assumed to be single-threaded. */ -void OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) +int OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) { - /* XXX TODO WARNING To be updated to return a value not assert. */ - assert(!stopped); + if (stopped) + return 0; - OPENSSL_init_crypto(opts | OPENSSL_INIT_ADD_ALL_CIPHERS - | OPENSSL_INIT_ADD_ALL_DIGESTS, settings); + if (!OPENSSL_init_crypto(opts | OPENSSL_INIT_ADD_ALL_CIPHERS + | OPENSSL_INIT_ADD_ALL_DIGESTS, settings)) + return 0; ossl_init_once_run(&ssl_base, ossl_init_ssl_base); @@ -314,5 +315,7 @@ void OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS *settings) if (opts & OPENSSL_INIT_LOAD_SSL_STRINGS) ossl_init_once_run(&ssl_strings, ossl_init_load_ssl_strings); + + return 1; } diff --git a/ssl/ssl_lib.c b/ssl/ssl_lib.c index e4b5d9f05..d0802207c 100644 --- a/ssl/ssl_lib.c +++ b/ssl/ssl_lib.c @@ -2270,7 +2270,8 @@ SSL_CTX *SSL_CTX_new(const SSL_METHOD *meth) return (NULL); } - OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL); + if (!OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL)) + return NULL; if (FIPS_mode() && (meth->version < TLS1_VERSION)) { SSLerr(SSL_F_SSL_CTX_NEW, SSL_R_AT_LEAST_TLS_1_0_NEEDED_IN_FIPS_MODE);