commit 1d1b723cc11bbfb87298df3fea3836b98914034a
parent 9afd8fb6252ec73829c4fc376a12bbf0f467642b
Author: David Goulet <dgoulet@torproject.org>
Date: Mon, 5 May 2025 15:40:05 +0000
Merge branch 'openssl_cleanup_part2_v2' into 'main'
Require OpenSSL >= 1.1.1 or LibreSSL >= 3.7
See merge request tpo/core/tor!885
Diffstat:
13 files changed, 67 insertions(+), 378 deletions(-)
diff --git a/changes/ticket41059 b/changes/ticket41059
@@ -0,0 +1,8 @@
+ o New system requirements:
+ - When built with OpenSSL, Tor now requires OpenSSL 1.1.1 or later.
+ (We strongly recommend 3.0 or later, but still build with 1.1.1,
+ even though it is not supported by the OpenSSL team,
+ due to its presence in Debian oldstable.)
+ Part of ticket 41059.
+ - When built with LibreSSL, Tor now requires LibreSSL 3.7 or later.
+ Part of ticket 41059.
diff --git a/configure.ac b/configure.ac
@@ -1000,7 +1000,7 @@ AC_ARG_WITH(ssl-dir,
fi
])
-AC_MSG_NOTICE([Now, we'll look for OpenSSL >= 1.0.1])
+AC_MSG_NOTICE([Now, we'll look for OpenSSL.])
TOR_SEARCH_LIBRARY(openssl, $tryssldir, [-lssl -lcrypto $TOR_LIB_GDI $TOR_LIB_WS32 $TOR_LIB_CRYPT32],
[#include <openssl/ssl.h>
char *getenv(const char *);],
@@ -1040,38 +1040,48 @@ dnl and later. We want to migrate away from them, but that will be a lot of
dnl work. (See ticket tor#40166.) For now, we disable the deprecation
dnl warnings.
-AC_MSG_CHECKING([for OpenSSL >= 3.0.0])
+AC_MSG_CHECKING([for OpenSSL implementation])
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
#include <openssl/opensslv.h>
-#if !defined(LIBRESSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER >= 0x30000000L
-#error "you_have_version_3"
+#if defined(LIBRESSL_VERSION_NUMBER)
+#error "this is libressl, no worries"
#endif
]], [[]])],
- [ AC_MSG_RESULT([no]) ],
- [ AC_MSG_RESULT([yes]);
- AC_DEFINE(OPENSSL_SUPPRESS_DEPRECATED, 1, [disable openssl deprecated-function warnings]) ])
-
-AC_MSG_CHECKING([for OpenSSL < 1.0.1])
+ [ openssl_impl=openssl
+ AC_MSG_RESULT([OpenSSL])
+ AC_DEFINE(OPENSSL_SUPPRESS_DEPRECATED, 1, [disable openssl deprecated-function warnings])
+ ],
+ [ openssl_impl=libressl
+ AC_MSG_RESULT([LibreSSL])
+ ])
+
+if test "x$openssl_impl" = "xopenssl"; then
+AC_MSG_CHECKING([for OpenSSL < 1.1.1])
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
#include <openssl/opensslv.h>
-#if OPENSSL_VERSION_NUMBER < 0x1000100fL
-#error "too old"
+#if !defined(LIBRESSL_VERSION_NUMBER) && OPENSSL_VERSION_NUMBER < 0x10101000L
+#error "openssl too old"
#endif
]], [[]])],
[ AC_MSG_RESULT([no]) ],
- [ AC_MSG_ERROR([OpenSSL is too old. We require 1.0.1 or later. You can specify a path to a newer one with --with-openssl-dir.]) ])
+ [ AC_MSG_RESULT([yes])
+ AC_MSG_ERROR([Your version of OpenSSL is too old. We require 1.1.1 or later, and you should use 3.5 if possible.])
+ ])
+fi
-AC_MSG_CHECKING([whether LibreSSL TLS 1.3 APIs are busted])
+if test "x$openssl_impl" = "xlibressl"; then
+AC_MSG_CHECKING([for LibreSSL < 3.7.0])
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
#include <openssl/opensslv.h>
-#if defined(LIBRESSL_VERSION_NUMBER) && \
- LIBRESSL_VERSION_NUMBER >= 0x3020100fL && \
- LIBRESSL_VERSION_NUMBER < 0x3040100fL
-#error "oh no"
+#if defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x3070000fL
+#error "libressl too old"
#endif
]], [[]])],
[ AC_MSG_RESULT([no]) ],
- [ AC_MSG_ERROR([This version of LibreSSL won't work with Tor. Please upgrade to LibreSSL 3.4.1 or later. (Or downgrade to 3.2.0 if you really must.)]) ])
+ [ AC_MSG_RESULT([yes])
+ AC_MSG_ERROR([Your version of LibreSSL is too old. We require 3.7.0 or later.])
+ ])
+fi
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[
#include <openssl/opensslv.h>
@@ -1108,10 +1118,6 @@ AC_RUN_IFELSE([AC_LANG_SOURCE([AC_LANG_PROGRAM([[
fi], [openssl_ver_mismatch=cross])
AC_MSG_RESULT([$openssl_ver_mismatch])
-AC_CHECK_MEMBERS([struct ssl_method_st.get_cipher_by_char], , ,
-[#include <openssl/ssl.h>
-])
-
dnl OpenSSL functions which we might not have. In theory, we could just
dnl check the openssl version number, but in practice that gets pretty
dnl confusing with LibreSSL, OpenSSL, and various distributions' patches
@@ -1126,15 +1132,6 @@ AC_CHECK_FUNCS([ \
TLS_method \
])
-dnl Check if OpenSSL structures are opaque
-AC_CHECK_MEMBERS([SSL.state], , ,
-[#include <openssl/ssl.h>
-])
-
-AC_CHECK_SIZEOF(SHA_CTX, , [AC_INCLUDES_DEFAULT()
-#include <openssl/sha.h>
-])
-
fi # enable_nss
dnl We will someday make KECCAK_TINY optional, but for now we still need
diff --git a/src/lib/crypt_ops/aes_openssl.c b/src/lib/crypt_ops/aes_openssl.c
@@ -24,10 +24,6 @@
#include <openssl/opensslv.h>
#include "lib/crypt_ops/crypto_openssl_mgt.h"
-#if OPENSSL_VERSION_NUMBER < OPENSSL_V_SERIES(1,0,0)
-#error "We require OpenSSL >= 1.0.0"
-#endif
-
DISABLE_GCC_WARNING("-Wredundant-decls")
#include <stdlib.h>
@@ -116,11 +112,7 @@ aes_cipher_free_(aes_cnt_cipher_t *cipher_)
if (!cipher_)
return;
EVP_CIPHER_CTX *cipher = (EVP_CIPHER_CTX *) cipher_;
-#ifdef OPENSSL_1_1_API
EVP_CIPHER_CTX_reset(cipher);
-#else
- EVP_CIPHER_CTX_cleanup(cipher);
-#endif
EVP_CIPHER_CTX_free(cipher);
}
void
diff --git a/src/lib/crypt_ops/compat_openssl.h b/src/lib/crypt_ops/compat_openssl.h
@@ -20,37 +20,13 @@
* \brief compatibility definitions for working with different openssl forks
**/
-#if OPENSSL_VERSION_NUMBER < OPENSSL_V_SERIES(1,0,1)
-#error "We require OpenSSL >= 1.0.1"
-#endif
-
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0)
-/* We define this macro if we're trying to build with the majorly refactored
- * API in OpenSSL 1.1 */
-#define OPENSSL_1_1_API
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0) && ... */
-
-/* LibreSSL claims to be OpenSSL 2.0 but lacks these OpenSSL 1.1 APIs */
-#if !defined(OPENSSL_1_1_API) || defined(LIBRESSL_VERSION_NUMBER)
+/* LibreSSL claims to be OpenSSL 2.0 but lacks this OpenSSL 1.1 API. */
+#if defined(LIBRESSL_VERSION_NUMBER)
#define RAND_OpenSSL() RAND_SSLeay()
-#define STATE_IS_SW_SERVER_HELLO(st) \
- (((st) == SSL3_ST_SW_SRVR_HELLO_A) || \
- ((st) == SSL3_ST_SW_SRVR_HELLO_B))
#define OSSL_HANDSHAKE_STATE int
-#define CONST_IF_OPENSSL_1_1_API
-#else
-#define STATE_IS_SW_SERVER_HELLO(st) \
- ((st) == TLS_ST_SW_SRVR_HELLO)
-#define CONST_IF_OPENSSL_1_1_API const
#endif
-/* OpenSSL 1.1 and LibreSSL both have these APIs */
-#ifndef OPENSSL_1_1_API
-#define OpenSSL_version(v) SSLeay_version(v)
-#define tor_OpenSSL_version_num() SSLeay()
-#else /* defined(OPENSSL_1_1_API) */
#define tor_OpenSSL_version_num() OpenSSL_version_num()
-#endif /* !defined(OPENSSL_1_1_API) */
#endif /* defined(ENABLE_OPENSSL) */
diff --git a/src/lib/crypt_ops/crypto_dh_openssl.c b/src/lib/crypt_ops/crypto_dh_openssl.c
@@ -60,7 +60,7 @@ crypto_validate_dh_params(const BIGNUM *p, const BIGNUM *g)
/* Copy into a temporary DH object, just so that DH_check() can be called. */
if (!(dh = DH_new()))
goto out;
-#ifdef OPENSSL_1_1_API
+
BIGNUM *dh_p, *dh_g;
if (!(dh_p = BN_dup(p)))
goto out;
@@ -68,12 +68,6 @@ crypto_validate_dh_params(const BIGNUM *p, const BIGNUM *g)
goto out;
if (!DH_set0_pqg(dh, dh_p, NULL, dh_g))
goto out;
-#else /* !defined(OPENSSL_1_1_API) */
- if (!(dh->p = BN_dup(p)))
- goto out;
- if (!(dh->g = BN_dup(g)))
- goto out;
-#endif /* defined(OPENSSL_1_1_API) */
/* Perform the validation. */
int codes = 0;
@@ -223,19 +217,12 @@ new_openssl_dh_from_params(BIGNUM *p, BIGNUM *g)
goto err;
}
-#ifdef OPENSSL_1_1_API
-
if (!DH_set0_pqg(res_dh, dh_p, NULL, dh_g)) {
goto err;
}
if (!DH_set_length(res_dh, DH_PRIVATE_KEY_BITS))
goto err;
-#else /* !defined(OPENSSL_1_1_API) */
- res_dh->p = dh_p;
- res_dh->g = dh_g;
- res_dh->length = DH_PRIVATE_KEY_BITS;
-#endif /* defined(OPENSSL_1_1_API) */
return res_dh;
@@ -276,9 +263,6 @@ crypto_dh_get_bytes(crypto_dh_t *dh)
int
crypto_dh_generate_public(crypto_dh_t *dh)
{
-#ifndef OPENSSL_1_1_API
- again:
-#endif
if (!DH_generate_key(dh->dh)) {
/* LCOV_EXCL_START
* To test this we would need some way to tell openssl to break DH. */
@@ -286,7 +270,7 @@ crypto_dh_generate_public(crypto_dh_t *dh)
return -1;
/* LCOV_EXCL_STOP */
}
-#ifdef OPENSSL_1_1_API
+
/* OpenSSL 1.1.x doesn't appear to let you regenerate a DH key, without
* recreating the DH object. I have no idea what sort of aliasing madness
* can occur here, so do the check, and just bail on failure.
@@ -298,20 +282,7 @@ crypto_dh_generate_public(crypto_dh_t *dh)
"the-universe chances really do happen. Treating as a failure.");
return -1;
}
-#else /* !defined(OPENSSL_1_1_API) */
- if (tor_check_dh_key(LOG_WARN, dh->dh->pub_key)<0) {
- /* LCOV_EXCL_START
- * If this happens, then openssl's DH implementation is busted. */
- log_warn(LD_CRYPTO, "Weird! Our own DH key was invalid. I guess once-in-"
- "the-universe chances really do happen. Trying again.");
- /* Free and clear the keys, so OpenSSL will actually try again. */
- BN_clear_free(dh->dh->pub_key);
- BN_clear_free(dh->dh->priv_key);
- dh->dh->pub_key = dh->dh->priv_key = NULL;
- goto again;
- /* LCOV_EXCL_STOP */
- }
-#endif /* defined(OPENSSL_1_1_API) */
+
return 0;
}
@@ -327,22 +298,14 @@ crypto_dh_get_public(crypto_dh_t *dh, char *pubkey, size_t pubkey_len)
const BIGNUM *dh_pub;
-#ifdef OPENSSL_1_1_API
const BIGNUM *dh_priv;
DH_get0_key(dh->dh, &dh_pub, &dh_priv);
-#else
- dh_pub = dh->dh->pub_key;
-#endif /* defined(OPENSSL_1_1_API) */
if (!dh_pub) {
if (crypto_dh_generate_public(dh)<0)
return -1;
else {
-#ifdef OPENSSL_1_1_API
DH_get0_key(dh->dh, &dh_pub, &dh_priv);
-#else
- dh_pub = dh->dh->pub_key;
-#endif
}
}
diff --git a/src/lib/crypt_ops/crypto_openssl_mgt.c b/src/lib/crypt_ops/crypto_openssl_mgt.c
@@ -45,19 +45,8 @@ ENABLE_GCC_WARNING("-Wredundant-decls")
#define DISABLE_ENGINES
#endif
-#ifndef NEW_THREAD_API
-/** A number of preallocated mutexes for use by OpenSSL. */
-static tor_mutex_t **openssl_mutexes_ = NULL;
-/** How many mutexes have we allocated for use by OpenSSL? */
-static int n_openssl_mutexes_ = 0;
-#endif /* !defined(NEW_THREAD_API) */
-
/** Declare STATIC functions */
STATIC char * parse_openssl_version_str(const char *raw_version);
-#ifndef NEW_THREAD_API
-STATIC void openssl_locking_cb_(int mode, int n, const char *file, int line);
-STATIC void tor_set_openssl_thread_id(CRYPTO_THREADID *threadid);
-#endif
/** Log all pending crypto errors at level <b>severity</b>. Use
* <b>doing</b> to describe our current activities.
@@ -106,12 +95,7 @@ static char *crypto_openssl_version_str = NULL;
const char *
crypto_openssl_get_version_str(void)
{
-#ifdef OPENSSL_VERSION
const int query = OPENSSL_VERSION;
-#else
- /* This old name was changed around OpenSSL 1.1.0 */
- const int query = SSLEAY_VERSION;
-#endif /* defined(OPENSSL_VERSION) */
if (crypto_openssl_version_str == NULL) {
const char *raw_version = OpenSSL_version(query);
@@ -120,8 +104,6 @@ crypto_openssl_get_version_str(void)
return crypto_openssl_version_str;
}
-#undef QUERY_OPENSSL_VERSION
-
static char *crypto_openssl_header_version_str = NULL;
/* Return a human-readable version of the compile-time openssl version
* number. */
@@ -142,46 +124,11 @@ crypto_openssl_get_header_version_str(void)
#endif
#endif /* !defined(COCCI) */
-#ifndef NEW_THREAD_API
-/** Helper: OpenSSL uses this callback to manipulate mutexes. */
-STATIC void
-openssl_locking_cb_(int mode, int n, const char *file, int line)
-{
- (void)file;
- (void)line;
- if (!openssl_mutexes_)
- /* This is not a really good fix for the
- * "release-freed-lock-from-separate-thread-on-shutdown" problem, but
- * it can't hurt. */
- return;
- if (mode & CRYPTO_LOCK)
- tor_mutex_acquire(openssl_mutexes_[n]);
- else
- tor_mutex_release(openssl_mutexes_[n]);
-}
-
-STATIC void
-tor_set_openssl_thread_id(CRYPTO_THREADID *threadid)
-{
- CRYPTO_THREADID_set_numeric(threadid, tor_get_thread_id());
-}
-#endif /* !defined(NEW_THREAD_API) */
-
/** Helper: Construct mutexes, and set callbacks to help OpenSSL handle being
* multithreaded. Returns 0. */
static int
setup_openssl_threading(void)
{
-#ifndef NEW_THREAD_API
- int i;
- int n = CRYPTO_num_locks();
- n_openssl_mutexes_ = n;
- openssl_mutexes_ = tor_calloc(n, sizeof(tor_mutex_t *));
- for (i=0; i < n; ++i)
- openssl_mutexes_[i] = tor_mutex_new();
- CRYPTO_set_locking_callback(openssl_locking_cb_);
- CRYPTO_THREADID_set_callback(tor_set_openssl_thread_id);
-#endif /* !defined(NEW_THREAD_API) */
return 0;
}
@@ -191,43 +138,19 @@ crypto_openssl_free_all(void)
{
tor_free(crypto_openssl_version_str);
tor_free(crypto_openssl_header_version_str);
-
- /* Destroying a locked mutex is undefined behaviour. This mutex may be
- * locked, because multiple threads can access it. But we need to destroy
- * it, otherwise re-initialisation will trigger undefined behaviour.
- * See #31735 for details. */
-#ifndef NEW_THREAD_API
- if (n_openssl_mutexes_) {
- int n = n_openssl_mutexes_;
- tor_mutex_t **ms = openssl_mutexes_;
- int i;
- openssl_mutexes_ = NULL;
- n_openssl_mutexes_ = 0;
- for (i=0;i<n;++i) {
- tor_mutex_free(ms[i]);
- }
- tor_free(ms);
- }
-#endif /* !defined(NEW_THREAD_API) */
}
/** Perform early (pre-configuration) initialization tasks for OpenSSL. */
void
crypto_openssl_early_init(void)
{
-#ifdef OPENSSL_1_1_API
OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS |
OPENSSL_INIT_LOAD_CRYPTO_STRINGS |
OPENSSL_INIT_ADD_ALL_CIPHERS |
OPENSSL_INIT_ADD_ALL_DIGESTS, NULL);
-#else /* !defined(OPENSSL_1_1_API) */
- ERR_load_crypto_strings();
- OpenSSL_add_all_algorithms();
-#endif /* defined(OPENSSL_1_1_API) */
setup_openssl_threading();
-#ifdef OPENSSL_1_1_API
unsigned long version_num = tor_OpenSSL_version_num();
const char *version_str = crypto_openssl_get_version_str();
if (version_num == OPENSSL_VERSION_NUMBER &&
@@ -249,7 +172,6 @@ crypto_openssl_early_init(void)
(unsigned long)OPENSSL_VERSION_NUMBER, OPENSSL_VERSION_TEXT,
version_num, version_str);
}
-#endif /* defined(OPENSSL_1_1_API) */
crypto_force_rand_ssleay();
}
@@ -352,12 +274,7 @@ crypto_openssl_init_engines(const char *accelName,
used by Tor and the set of algorithms available in the engine */
log_engine("RSA", ENGINE_get_default_RSA());
log_engine("DH", ENGINE_get_default_DH());
-#ifdef OPENSSL_1_1_API
log_engine("EC", ENGINE_get_default_EC());
-#else
- log_engine("ECDH", ENGINE_get_default_ECDH());
- log_engine("ECDSA", ENGINE_get_default_ECDSA());
-#endif /* defined(OPENSSL_1_1_API) */
log_engine("RAND", ENGINE_get_default_RAND());
log_engine("RAND (which we will not use)", ENGINE_get_default_RAND());
log_engine("SHA1", ENGINE_get_digest_engine(NID_sha1));
@@ -384,6 +301,14 @@ int
crypto_openssl_late_init(int useAccel, const char *accelName,
const char *accelDir)
{
+ if (tor_OpenSSL_version_num() < OPENSSL_V_SERIES(3,0,0)) {
+ log_warn(LD_CRYPTO, "Running with OpenSSL version \"%s\", "
+ "which is no longer maintained by the OpenSSL project. "
+ "We recommend that you upgrade to OpenSSL 3.0 or later. "
+ "OpenSSL >=3.5 would be ideal.",
+ OPENSSL_VERSION_TEXT);
+ }
+
if (useAccel > 0) {
if (crypto_openssl_init_engines(accelName, accelDir) < 0)
return -1;
@@ -406,35 +331,13 @@ crypto_openssl_late_init(int useAccel, const char *accelName,
void
crypto_openssl_thread_cleanup(void)
{
-#ifndef NEW_THREAD_API
- ERR_remove_thread_state(NULL);
-#endif
}
/** Clean up global resources held by openssl. */
void
crypto_openssl_global_cleanup(void)
{
-#ifndef OPENSSL_1_1_API
- EVP_cleanup();
-#endif
-#ifndef NEW_THREAD_API
- ERR_remove_thread_state(NULL);
-#endif
-#ifndef OPENSSL_1_1_API
- ERR_free_strings();
-#endif
-
-#ifndef DISABLE_ENGINES
-#ifndef OPENSSL_1_1_API
- ENGINE_cleanup();
-#endif
-#endif
-
CONF_modules_unload(1);
-#ifndef OPENSSL_1_1_API
- CRYPTO_cleanup_all_ex_data();
-#endif
crypto_openssl_free_all();
}
diff --git a/src/lib/crypt_ops/crypto_openssl_mgt.h b/src/lib/crypt_ops/crypto_openssl_mgt.h
@@ -49,21 +49,6 @@
#define OPENSSL_V_SERIES(a,b,c) \
OPENSSL_VER((a),(b),(c),0,0)
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_VER(1,1,0,0,5)
-/* OpenSSL as of 1.1.0pre4 has an "new" thread API, which doesn't require
- * setting up various callbacks.
- *
- * OpenSSL 1.1.0pre4 has a messed up `ERR_remove_thread_state()` prototype,
- * while the previous one was restored in pre5, and the function made a no-op
- * (along with a deprecated annotation, which produces a compiler warning).
- *
- * While it is possible to support all three versions of the thread API,
- * a version that existed only for one snapshot pre-release is kind of
- * pointless, so let's not.
- */
-#define NEW_THREAD_API
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_VER(1,1,0,0,5) && ... */
-
void crypto_openssl_log_errors(int severity, const char *doing);
/* global openssl state */
diff --git a/src/lib/crypt_ops/crypto_rsa_openssl.c b/src/lib/crypt_ops/crypto_rsa_openssl.c
@@ -47,16 +47,12 @@ struct crypto_pk_t
int
crypto_pk_key_is_private(const crypto_pk_t *k)
{
-#ifdef OPENSSL_1_1_API
if (!k || !k->key)
return 0;
const BIGNUM *p, *q;
RSA_get0_factors(k->key, &p, &q);
return p != NULL; /* XXX/yawning: Should we check q? */
-#else /* !defined(OPENSSL_1_1_API) */
- return k && k->key && k->key->p;
-#endif /* defined(OPENSSL_1_1_API) */
}
/** used by tortls.c: wrap an RSA* in a crypto_pk_t. Takes ownership of
@@ -212,12 +208,8 @@ crypto_pk_public_exponent_ok(const crypto_pk_t *env)
const BIGNUM *e;
-#ifdef OPENSSL_1_1_API
const BIGNUM *n, *d;
RSA_get0_key(env->key, &n, &e, &d);
-#else
- e = env->key->e;
-#endif /* defined(OPENSSL_1_1_API) */
return BN_is_word(e, TOR_RSA_EXPONENT);
}
@@ -242,16 +234,9 @@ crypto_pk_cmp_keys(const crypto_pk_t *a, const crypto_pk_t *b)
const BIGNUM *a_n, *a_e;
const BIGNUM *b_n, *b_e;
-#ifdef OPENSSL_1_1_API
const BIGNUM *a_d, *b_d;
RSA_get0_key(a->key, &a_n, &a_e, &a_d);
RSA_get0_key(b->key, &b_n, &b_e, &b_d);
-#else
- a_n = a->key->n;
- a_e = a->key->e;
- b_n = b->key->n;
- b_e = b->key->e;
-#endif /* defined(OPENSSL_1_1_API) */
tor_assert(a_n != NULL && a_e != NULL);
tor_assert(b_n != NULL && b_e != NULL);
@@ -279,7 +264,6 @@ crypto_pk_num_bits(crypto_pk_t *env)
tor_assert(env);
tor_assert(env->key);
-#ifdef OPENSSL_1_1_API
/* It's so stupid that there's no other way to check that n is valid
* before calling RSA_bits().
*/
@@ -288,10 +272,6 @@ crypto_pk_num_bits(crypto_pk_t *env)
tor_assert(n != NULL);
return RSA_bits(env->key);
-#else /* !defined(OPENSSL_1_1_API) */
- tor_assert(env->key->n);
- return BN_num_bits(env->key->n);
-#endif /* defined(OPENSSL_1_1_API) */
}
/** Increase the reference count of <b>env</b>, and return it.
@@ -572,11 +552,7 @@ static bool
rsa_private_key_too_long(RSA *rsa, int max_bits)
{
const BIGNUM *n, *e, *p, *q, *d, *dmp1, *dmq1, *iqmp;
-#if defined(OPENSSL_1_1_API) && \
- (!defined(LIBRESSL_VERSION_NUMBER) || \
- LIBRESSL_VERSION_NUMBER >= OPENSSL_V_SERIES(3,5,0))
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,1)
n = RSA_get0_n(rsa);
e = RSA_get0_e(rsa);
p = RSA_get0_p(rsa);
@@ -585,24 +561,9 @@ rsa_private_key_too_long(RSA *rsa, int max_bits)
dmp1 = RSA_get0_dmp1(rsa);
dmq1 = RSA_get0_dmq1(rsa);
iqmp = RSA_get0_iqmp(rsa);
-#else /* !(OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,1)) */
- /* The accessors above did not exist in openssl 1.1.0. */
- p = q = dmp1 = dmq1 = iqmp = NULL;
- RSA_get0_key(rsa, &n, &e, &d);
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,1) */
if (RSA_bits(rsa) > max_bits)
return true;
-#else /* !defined(OPENSSL_1_1_API) && ... */
- n = rsa->n;
- e = rsa->e;
- p = rsa->p;
- q = rsa->q;
- d = rsa->d;
- dmp1 = rsa->dmp1;
- dmq1 = rsa->dmq1;
- iqmp = rsa->iqmp;
-#endif /* defined(OPENSSL_1_1_API) && ... */
if (n && BN_num_bits(n) > max_bits)
return true;
diff --git a/src/lib/tls/tortls_openssl.c b/src/lib/tls/tortls_openssl.c
@@ -80,14 +80,6 @@ ENABLE_GCC_WARNING("-Wredundant-decls")
#define ADDR(tls) (((tls) && (tls)->address) ? tls->address : "peer")
-#if OPENSSL_VERSION_NUMBER < OPENSSL_V(1,0,0,'f')
-/* This is a version of OpenSSL before 1.0.0f. It does not have
- * the CVE-2011-4576 fix, and as such it can't use RELEASE_BUFFERS and
- * SSL3 safely at the same time.
- */
-#define DISABLE_SSL3_HANDSHAKE
-#endif /* OPENSSL_VERSION_NUMBER < OPENSSL_V(1,0,0,'f') */
-
/** Set to true iff openssl bug 7712 has been detected. */
static int openssl_bug_7712_is_present = 0;
@@ -179,9 +171,6 @@ tor_tls_log_one_error(tor_tls_t *tls, unsigned long err,
case SSL_R_HTTP_REQUEST:
case SSL_R_HTTPS_PROXY_REQUEST:
case SSL_R_RECORD_LENGTH_MISMATCH:
-#ifndef OPENSSL_1_1_API
- case SSL_R_RECORD_TOO_LARGE:
-#endif
case SSL_R_UNKNOWN_PROTOCOL:
case SSL_R_UNSUPPORTED_PROTOCOL:
severity = LOG_INFO;
@@ -304,21 +293,14 @@ tor_tls_init(void)
check_no_tls_errors();
if (!tls_library_is_initialized) {
-#ifdef OPENSSL_1_1_API
OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL);
-#else
- SSL_library_init();
- SSL_load_error_strings();
-#endif /* defined(OPENSSL_1_1_API) */
-
-#if (SIZEOF_VOID_P >= 8 && \
- OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,0,1) && \
- (!defined(LIBRESSL_VERSION_NUMBER) || \
- LIBRESSL_VERSION_NUMBER < 0x3080000fL))
- long version = tor_OpenSSL_version_num();
+#if (SIZEOF_VOID_P >= 8)
/* LCOV_EXCL_START : we can't test these lines on the same machine */
- if (version >= OPENSSL_V_SERIES(1,0,1)) {
+ {
+ /* TODO: I'm not sure that this test is still necessary on our
+ * supported openssl/libressl versions. */
+
/* Warn if we could *almost* be running with much faster ECDH.
If we're built for a 64-bit target, using OpenSSL 1.0.1, but we
don't have one of the built-in __uint128-based speedups, we are
@@ -345,7 +327,7 @@ tor_tls_init(void)
"when configuring it) would make ECDH much faster.");
}
/* LCOV_EXCL_STOP */
-#endif /* (SIZEOF_VOID_P >= 8 && ... */
+#endif /* (SIZEOF_VOID_P >= 8 */
tor_tls_allocate_tor_tls_object_ex_data_index();
@@ -581,12 +563,6 @@ tor_tls_context_new(crypto_pk_t *identity, unsigned int key_lifetime,
#ifdef SSL_OP_NO_COMPRESSION
SSL_CTX_set_options(result->ctx, SSL_OP_NO_COMPRESSION);
#endif
-#if OPENSSL_VERSION_NUMBER < OPENSSL_V_SERIES(1,1,0)
-#ifndef OPENSSL_NO_COMP
- if (result->ctx->comp_methods)
- result->ctx->comp_methods = NULL;
-#endif
-#endif /* OPENSSL_VERSION_NUMBER < OPENSSL_V_SERIES(1,1,0) */
#ifdef SSL_MODE_RELEASE_BUFFERS
SSL_CTX_set_mode(result->ctx, SSL_MODE_RELEASE_BUFFERS);
@@ -1051,18 +1027,9 @@ tor_tls_get_n_raw_bytes(tor_tls_t *tls, size_t *n_read, size_t *n_written)
* save the original BIO for tls->ssl in the tor_tls_t structure, but
* that would be tempting fate. */
wbio = SSL_get_wbio(tls->ssl);
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_VER(1,1,0,0,5)
- /* BIO structure is opaque as of OpenSSL 1.1.0-pre5-dev. Again, not
- * supposed to use this form of the version macro, but the OpenSSL developers
- * introduced major API changes in the pre-release stage.
- */
if (BIO_method_type(wbio) == BIO_TYPE_BUFFER &&
(tmpbio = BIO_next(wbio)) != NULL)
wbio = tmpbio;
-#else /* !(OPENSSL_VERSION_NUMBER >= OPENSSL_VER(1,1,0,0,5)) */
- if (wbio->method == BIO_f_buffer() && (tmpbio = BIO_next(wbio)) != NULL)
- wbio = tmpbio;
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_VER(1,1,0,0,5) */
w = (unsigned long) BIO_number_written(wbio);
/* We are ok with letting these unsigned ints go "negative" here:
@@ -1173,7 +1140,6 @@ tor_tls_get_buffer_sizes(tor_tls_t *tls,
size_t *rbuf_capacity, size_t *rbuf_bytes,
size_t *wbuf_capacity, size_t *wbuf_bytes)
{
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0)
(void)tls;
(void)rbuf_capacity;
(void)rbuf_bytes;
@@ -1181,19 +1147,6 @@ tor_tls_get_buffer_sizes(tor_tls_t *tls,
(void)wbuf_bytes;
return -1;
-#else /* !(OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0)) */
- if (tls->ssl->s3->rbuf.buf)
- *rbuf_capacity = tls->ssl->s3->rbuf.len;
- else
- *rbuf_capacity = 0;
- if (tls->ssl->s3->wbuf.buf)
- *wbuf_capacity = tls->ssl->s3->wbuf.len;
- else
- *wbuf_capacity = 0;
- *rbuf_bytes = tls->ssl->s3->rbuf.left;
- *wbuf_bytes = tls->ssl->s3->wbuf.left;
- return 0;
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0) */
}
/** Check whether the ECC group requested is supported by the current OpenSSL
diff --git a/src/lib/tls/x509_openssl.c b/src/lib/tls/x509_openssl.c
@@ -46,7 +46,6 @@ ENABLE_GCC_WARNING("-Wredundant-decls")
#include <stdlib.h>
#include <string.h>
-#ifdef OPENSSL_1_1_API
#define X509_get_notBefore_const(cert) \
X509_get0_notBefore(cert)
#define X509_get_notAfter_const(cert) \
@@ -59,12 +58,6 @@ ENABLE_GCC_WARNING("-Wredundant-decls")
#define X509_get_notAfter(cert) \
X509_getm_notAfter(cert)
#endif
-#else /* !defined(OPENSSL_1_1_API) */
-#define X509_get_notBefore_const(cert) \
- ((const ASN1_TIME*) X509_get_notBefore((X509 *)cert))
-#define X509_get_notAfter_const(cert) \
- ((const ASN1_TIME*) X509_get_notAfter((X509 *)cert))
-#endif /* defined(OPENSSL_1_1_API) */
/** Return a newly allocated X509 name with commonName <b>cname</b>. */
static X509_NAME *
@@ -329,11 +322,7 @@ tor_tls_cert_is_valid(int severity,
cert_key = X509_get_pubkey(cert->cert);
if (check_rsa_1024 && cert_key) {
RSA *rsa = EVP_PKEY_get1_RSA(cert_key);
-#ifdef OPENSSL_1_1_API
if (rsa && RSA_bits(rsa) == 1024) {
-#else
- if (rsa && BN_num_bits(rsa->n) == 1024) {
-#endif
key_ok = 1;
} else {
log_fn(severity, LD_CRYPTO, "Invalid certificate: Key is not RSA1024.");
diff --git a/src/test/test_crypto.c b/src/test/test_crypto.c
@@ -187,12 +187,8 @@ test_crypto_dh(void *arg)
dh4 = crypto_dh_new_openssl_tls();
tt_assert(DH_generate_key(dh4));
const BIGNUM *pk=NULL;
-#ifdef OPENSSL_1_1_API
const BIGNUM *sk=NULL;
DH_get0_key(dh4, &pk, &sk);
-#else
- pk = dh4->pub_key;
-#endif /* defined(OPENSSL_1_1_API) */
tt_assert(pk);
tt_int_op(BN_num_bytes(pk), OP_LE, DH1024_KEY_LEN);
tt_int_op(BN_num_bytes(pk), OP_GT, 0);
diff --git a/src/test/test_crypto_openssl.c b/src/test/test_crypto_openssl.c
@@ -49,11 +49,6 @@ test_crypto_rng_engine(void *arg)
;
}
-#ifndef OPENSSL_1_1_API
-#define EVP_ENCODE_CTX_new() tor_malloc_zero(sizeof(EVP_ENCODE_CTX))
-#define EVP_ENCODE_CTX_free(ctx) tor_free(ctx)
-#endif
-
/** Encode src into dest with OpenSSL's EVP Encode interface, returning the
* length of the encoded data in bytes.
*/
diff --git a/src/test/test_tortls_openssl.c b/src/test/test_tortls_openssl.c
@@ -46,15 +46,19 @@ ENABLE_GCC_WARNING("-Wredundant-decls")
#include "test/log_test_helpers.h"
#include "test/test_tortls.h"
-#ifndef HAVE_SSL_STATE
-#define OPENSSL_OPAQUE
-#endif
-
-#if defined(OPENSSL_OPAQUE) && !defined(LIBRESSL_VERSION_NUMBER)
#define SSL_STATE_STR "before SSL initialization"
-#else
-#define SSL_STATE_STR "before/accept initialization"
-#endif
+
+/* Every version and fork of OpenSSL we support now qualifies as "opaque",
+ * in that it hides the members of important structures.
+ *
+ * That's a good thing, but it means we can't run a number of older tests
+ * that require the ability to poke at OpenSSL's internals.
+ *
+ * We're retaining these tests here, rather than removing them,
+ * in case anybody wants to port them to modern OpenSSL.
+ * (Some of them are probably not worth saving, though.)
+ */
+#define OPENSSL_OPAQUE
#ifndef OPENSSL_OPAQUE
static SSL_METHOD *
@@ -124,12 +128,7 @@ test_tortls_tor_tls_new(void *data)
static void
library_init(void)
{
-#ifdef OPENSSL_1_1_API
OPENSSL_init_ssl(OPENSSL_INIT_LOAD_SSL_STRINGS, NULL);
-#else
- SSL_library_init();
- SSL_load_error_strings();
-#endif /* defined(OPENSSL_1_1_API) */
}
static void
@@ -296,13 +295,6 @@ test_tortls_log_one_error(void *ignored)
LOG_WARN, 0, NULL);
expect_log_severity(LOG_INFO);
-#ifndef OPENSSL_1_1_API
- mock_clean_saved_logs();
- tor_tls_log_one_error(tls, ERR_PACK(1, 2, SSL_R_RECORD_TOO_LARGE),
- LOG_WARN, 0, NULL);
- expect_log_severity(LOG_INFO);
-#endif /* !defined(OPENSSL_1_1_API) */
-
mock_clean_saved_logs();
tor_tls_log_one_error(tls, ERR_PACK(1, 2, SSL_R_UNKNOWN_PROTOCOL),
LOG_WARN, 0, NULL);
@@ -721,23 +713,7 @@ test_tortls_get_buffer_sizes(void *ignored)
tls->ssl->s3->wbuf.left = 43;
ret = tor_tls_get_buffer_sizes(tls, &rbuf_c, &rbuf_b, &wbuf_c, &wbuf_b);
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0)
tt_int_op(ret, OP_EQ, -1);
-#else
- tt_int_op(ret, OP_EQ, 0);
- tt_int_op(rbuf_c, OP_EQ, 0);
- tt_int_op(wbuf_c, OP_EQ, 0);
- tt_int_op(rbuf_b, OP_EQ, 42);
- tt_int_op(wbuf_b, OP_EQ, 43);
-
- tls->ssl->s3->rbuf.buf = tor_malloc_zero(1);
- tls->ssl->s3->wbuf.buf = tor_malloc_zero(1);
- ret = tor_tls_get_buffer_sizes(tls, &rbuf_c, &rbuf_b, &wbuf_c, &wbuf_b);
- tt_int_op(ret, OP_EQ, 0);
- tt_int_op(rbuf_c, OP_EQ, 1);
- tt_int_op(wbuf_c, OP_EQ, 2);
-
-#endif /* OPENSSL_VERSION_NUMBER >= OPENSSL_V_SERIES(1,1,0) */
done:
tor_free(tls->ssl->s3->rbuf.buf);
@@ -914,11 +890,6 @@ test_tortls_block_renegotiation(void *ignored)
tor_tls_block_renegotiation(tls);
-#ifndef OPENSSL_1_1_API
- tt_assert(!(tls->ssl->s3->flags &
- SSL3_FLAGS_ALLOW_UNSAFE_LEGACY_RENEGOTIATION));
-#endif
-
done:
tor_free(tls->ssl->s3);
tor_free(tls->ssl);