Blame SOURCES/corefx-openssl-0005-Make-portable-builds-work-across-OpenSSL-1.0.2-1.1.1.patch

debe55
From 07c2b5773e994e8922a24757605a5eff05073167 Mon Sep 17 00:00:00 2001
debe55
From: Jeremy Barton <jbarton@microsoft.com>
debe55
Date: Wed, 14 Apr 2021 16:38:19 -0700
debe55
Subject: [PATCH 05/11] Make portable builds work across OpenSSL
debe55
 1.0.2/1.1.1/3.0
debe55
debe55
Overall structure of changes
debe55
debe55
* Pull compatibility headers out into separate include files, because opensslshim.h is too big.
debe55
* Use forward definition of EVP_PKEY_CTX_set_rsa_keygen_bits and friends.
debe55
  * These are in a new apibridge file because they're for bridging up to 3.0, and the existing one was for 1.1(.1)
debe55
  * Some constants needed for this file changed between 1.1 and 3.0, so there are a lot of asserts and redefines.
debe55
* On OpenSSL 3.0, build a legacy version of ERR_put_error since it has the easier signature to work with.
debe55
* FALLBACK_FUNCTION doesn't care which version it bound to, if it doesn't find it use a local_ function.
debe55
* Renamed NEW_REQUIRED_FUNCTION to REQUIRED_FUNCTION_110 because "new" is now "sort of old".
debe55
* There's a manual sanity test that either ERR_put_error or the three new functions that together replace it are found, so we don't end up in a state where we can't report shim-injected errors.
debe55
debe55
Portable build checker:
debe55
* Built with OpenSSL 1.0.2 headers (Ubuntu 16.04 default libssl-dev)
debe55
  * Ran with 1.0.2 (Ubuntu 16.04 default libssl)
debe55
  * Ran with 1.1.1 (Ubuntu 18.04 default libssl)
debe55
  * Ran with 3.0 (Ubuntu 16.04 with local build of OpenSSL 3.0 alpha 13)
debe55
* Built with OpenSSL 1.1.1 headers (Ubuntu 18.04 default libssl-dev)
debe55
  * Ran with 1.0.2 (Ubuntu 16.04 default libssl)
debe55
  * Ran with 1.1.1 (Ubuntu 18.04 default libssl)
debe55
  * Ran with 3.0 (Ubuntu 16.04 with local build of OpenSSL 3.0 alpha 13)
debe55
* Built with OpenSSL 3.0 headers (Ubuntu 16.04 with local build of OpenSSL 3.0 alpha 13 and some surgery to the extra_libs.cmake)
debe55
  * Ran with 1.0.2 (Ubuntu 16.04 default libssl)
debe55
  * Ran with 1.1.1 (Ubuntu 18.04 default libssl)
debe55
  * Ran with 3.0 (Ubuntu 16.04 with local build of OpenSSL 3.0 alpha 13)
debe55
debe55
3.0 doesn't run error-free, but it runs with the same error rate from portable and direct builds.   All verification was limited to the System.Security.Cryptography.Algorithms.Tests run, but that's generally representative of the bindings.
debe55
---
debe55
 .../CMakeLists.txt                            |   1 +
debe55
 .../apibridge_30.c                            | 104 +++++++++
debe55
 .../apibridge_30.h                            |  13 ++
debe55
 .../apibridge_30_rev.h                        |  10 +
debe55
 .../openssl.c                                 |   2 +-
debe55
 .../opensslshim.c                             |  29 ++-
debe55
 .../opensslshim.h                             | 204 +++++++-----------
debe55
 .../osslcompat_102.h                          |  34 +++
debe55
 .../osslcompat_111.h                          |  80 +++++++
debe55
 .../osslcompat_30.h                           |  23 ++
debe55
 .../pal_ssl.c                                 |   2 +-
debe55
 11 files changed, 367 insertions(+), 135 deletions(-)
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.c
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.h
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/apibridge_30_rev.h
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/osslcompat_102.h
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/osslcompat_111.h
debe55
 create mode 100644 src/Native/Unix/System.Security.Cryptography.Native/osslcompat_30.h
debe55
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/CMakeLists.txt b/src/Native/Unix/System.Security.Cryptography.Native/CMakeLists.txt
debe55
index b2f4e33f0b..19dab3035d 100644
debe55
--- a/src/Native/Unix/System.Security.Cryptography.Native/CMakeLists.txt
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/CMakeLists.txt
debe55
@@ -23,6 +23,7 @@ include_directories(${OPENSSL_INCLUDE_DIR})
debe55
 
debe55
 set(NATIVECRYPTO_SOURCES
debe55
     apibridge.c
debe55
+    apibridge_30.c
debe55
     openssl.c
debe55
     pal_asn1.c
debe55
     pal_bignum.c
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.c b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.c
debe55
new file mode 100644
debe55
index 0000000000..63b5531863
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.c
debe55
@@ -0,0 +1,104 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+
debe55
+#include "opensslshim.h"
debe55
+#include "pal_crypto_types.h"
debe55
+#include "pal_types.h"
debe55
+
debe55
+#include "../Common/pal_safecrt.h"
debe55
+#include <assert.h>
debe55
+
debe55
+#if defined NEED_OPENSSL_1_0 || defined NEED_OPENSSL_1_1
debe55
+
debe55
+#include "apibridge_30.h"
debe55
+
debe55
+// 1.0 and 1.1 agree on the values of the EVP_PKEY_ values, but some of them changed in 3.0.
debe55
+// If we're running on 3.0 we already call the real methods, not these fallbacks, so we need to always use
debe55
+// the 1.0/1.1 values here.
debe55
+
debe55
+// These values are in common.
debe55
+c_static_assert(EVP_PKEY_CTRL_MD == 1);
debe55
+c_static_assert(EVP_PKEY_CTRL_RSA_KEYGEN_BITS == 0x1003);
debe55
+c_static_assert(EVP_PKEY_CTRL_RSA_OAEP_MD == 0x1009);
debe55
+c_static_assert(EVP_PKEY_CTRL_RSA_PADDING == 0x1001);
debe55
+c_static_assert(EVP_PKEY_CTRL_RSA_PSS_SALTLEN == 0x1002);
debe55
+c_static_assert(EVP_PKEY_OP_KEYGEN == (1 << 2));
debe55
+c_static_assert(EVP_PKEY_RSA == 6);
debe55
+
debe55
+#if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_3_0_RTM
debe55
+
debe55
+c_static_assert(EVP_PKEY_OP_SIGN == (1 << 3));
debe55
+c_static_assert(EVP_PKEY_OP_VERIFY == (1 << 4));
debe55
+c_static_assert(EVP_PKEY_OP_TYPE_CRYPT == ((1 << 8) | (1 << 9)));
debe55
+c_static_assert(EVP_PKEY_OP_TYPE_SIG == 0xF8);
debe55
+
debe55
+#else
debe55
+
debe55
+#undef EVP_PKEY_OP_SIGN
debe55
+#define EVP_PKEY_OP_SIGN (1 << 3)
debe55
+#undef EVP_PKEY_OP_VERIFY
debe55
+#define EVP_PKEY_OP_VERIFY (1 << 4)
debe55
+#undef EVP_PKEY_OP_TYPE_CRYPT
debe55
+#define EVP_PKEY_OP_TYPE_CRYPT ((1 << 8) | (1 << 9))
debe55
+#undef EVP_PKEY_OP_TYPE_SIG
debe55
+#define EVP_PKEY_OP_TYPE_SIG 0xF8 // OP_SIGN | OP_VERIFY | OP_VERIFYRECOVER | OP_SIGNCTX | OP_VERIFYCTX
debe55
+
debe55
+#endif
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_rsa_keygen_bits(EVP_PKEY_CTX* ctx, int bits)
debe55
+{
debe55
+    return RSA_pkey_ctx_ctrl(ctx, EVP_PKEY_OP_KEYGEN, EVP_PKEY_CTRL_RSA_KEYGEN_BITS, bits, NULL);
debe55
+}
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_rsa_oaep_md(EVP_PKEY_CTX* ctx, const EVP_MD* md)
debe55
+{
debe55
+    // set_rsa_oaep_md doesn't route through RSA_pkey_ctx_ctrl n 1.1, unlike the other set_rsa operations.
debe55
+#pragma clang diagnostic push
debe55
+#pragma clang diagnostic ignored "-Wcast-qual"
debe55
+    return EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA, EVP_PKEY_OP_TYPE_CRYPT, EVP_PKEY_CTRL_RSA_OAEP_MD, 0, (void*)md);
debe55
+#pragma clang diagnostic pop
debe55
+}
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_rsa_padding(EVP_PKEY_CTX* ctx, int pad_mode)
debe55
+{
debe55
+    return RSA_pkey_ctx_ctrl(ctx, -1, EVP_PKEY_CTRL_RSA_PADDING, pad_mode, NULL);
debe55
+}
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_rsa_pss_saltlen(EVP_PKEY_CTX* ctx, int saltlen)
debe55
+{
debe55
+    return RSA_pkey_ctx_ctrl(
debe55
+        ctx, (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_VERIFY), EVP_PKEY_CTRL_RSA_PSS_SALTLEN, saltlen, NULL);
debe55
+}
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_signature_md(EVP_PKEY_CTX* ctx, const EVP_MD* md)
debe55
+{
debe55
+#pragma clang diagnostic push
debe55
+#pragma clang diagnostic ignored "-Wcast-qual"
debe55
+    return EVP_PKEY_CTX_ctrl(ctx, -1, EVP_PKEY_OP_TYPE_SIG, EVP_PKEY_CTRL_MD, 0, (void*)md);
debe55
+#pragma clang diagnostic pop
debe55
+}
debe55
+
debe55
+#endif // defined NEED_OPENSSL_1_0 || defined NEED_OPENSSL_1_1
debe55
+
debe55
+#ifdef NEED_OPENSSL_3_0
debe55
+
debe55
+#include "apibridge_30_rev.h"
debe55
+
debe55
+void local_ERR_put_error(int32_t lib, int32_t func, int32_t reason, const char* file, int32_t line)
debe55
+{
debe55
+    // In portable builds, ensure that we found the 3.0 error reporting functions.
debe55
+    // In non-portable builds, this is just assert(true), but then we call the functions,
debe55
+    // so the compiler ensures they're there anyways.
debe55
+    assert(API_EXISTS(ERR_new) && API_EXISTS(ERR_set_debug) && API_EXISTS(ERR_set_error));
debe55
+    ERR_new();
debe55
+
debe55
+    // ERR_set_debug saves only the pointer, not the value, as it expects constants.
debe55
+    // So just ignore the legacy numeric code, and use the 3.0 "Uh, I don't know"
debe55
+    // function name.
debe55
+    (void)func;
debe55
+    ERR_set_debug(file, line, "(unknown function)");
debe55
+
debe55
+    ERR_set_error(lib, reason, NULL);
debe55
+}
debe55
+
debe55
+#endif // defined NEED_OPENSSL_3_0
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.h b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.h
debe55
new file mode 100644
debe55
index 0000000000..0f28900cb7
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30.h
debe55
@@ -0,0 +1,13 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+
debe55
+// Functions based on OpenSSL 3.0 API, used when building against/running with older versions.
debe55
+
debe55
+#pragma once
debe55
+#include "pal_types.h"
debe55
+
debe55
+int local_EVP_PKEY_CTX_set_rsa_keygen_bits(EVP_PKEY_CTX* ctx, int bits);
debe55
+int local_EVP_PKEY_CTX_set_rsa_oaep_md(EVP_PKEY_CTX* ctx, const EVP_MD* md);
debe55
+int local_EVP_PKEY_CTX_set_rsa_padding(EVP_PKEY_CTX* ctx, int pad_mode);
debe55
+int local_EVP_PKEY_CTX_set_rsa_pss_saltlen(EVP_PKEY_CTX* ctx, int saltlen);
debe55
+int local_EVP_PKEY_CTX_set_signature_md(EVP_PKEY_CTX* ctx, const EVP_MD* md);
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30_rev.h b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30_rev.h
debe55
new file mode 100644
debe55
index 0000000000..657cc969d2
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/apibridge_30_rev.h
debe55
@@ -0,0 +1,10 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+
debe55
+// Functions based on OpenSSL 3.0 API, used when building against/running with older versions.
debe55
+
debe55
+#pragma once
debe55
+#include "pal_types.h"
debe55
+
debe55
+// For 3.0 to behave like previous versions.
debe55
+void local_ERR_put_error(int32_t lib, int32_t func, int32_t reason, const char* file, int32_t line);
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/openssl.c b/src/Native/Unix/System.Security.Cryptography.Native/openssl.c
debe55
index 1a9ea04839..456741360d 100644
debe55
--- a/src/Native/Unix/System.Security.Cryptography.Native/openssl.c
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/openssl.c
debe55
@@ -1256,7 +1256,7 @@ done:
debe55
 }
debe55
 #endif // NEED_OPENSSL_1_0 */
debe55
 
debe55
-#ifdef NEED_OPENSSL_1_1
debe55
+#if defined NEED_OPENSSL_1_1 || defined NEED_OPENSSL_3_0
debe55
 
debe55
 // Only defined in OpenSSL 1.1.1+, has no effect on 1.1.0.
debe55
 #ifndef OPENSSL_INIT_NO_ATEXIT
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.c b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.c
debe55
index b085114a6b..edd7a6dd2d 100644
debe55
--- a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.c
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.c
debe55
@@ -13,7 +13,7 @@
debe55
 
debe55
 // Define pointers to all the used OpenSSL functions
debe55
 #define REQUIRED_FUNCTION(fn) __typeof(fn) fn##_ptr;
debe55
-#define NEW_REQUIRED_FUNCTION(fn) __typeof(fn) fn##_ptr;
debe55
+#define REQUIRED_FUNCTION_110(fn) __typeof(fn) fn##_ptr;
debe55
 #define LIGHTUP_FUNCTION(fn) __typeof(fn) fn##_ptr;
debe55
 #define FALLBACK_FUNCTION(fn) __typeof(fn) fn##_ptr;
debe55
 #define RENAMED_FUNCTION(fn,oldfn) __typeof(fn) fn##_ptr;
debe55
@@ -23,7 +23,7 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #undef RENAMED_FUNCTION
debe55
 #undef FALLBACK_FUNCTION
debe55
 #undef LIGHTUP_FUNCTION
debe55
-#undef NEW_REQUIRED_FUNCTION
debe55
+#undef REQUIRED_FUNCTION_110
debe55
 #undef REQUIRED_FUNCTION
debe55
 
debe55
 // x.x.x, considering the max number of decimal digits for each component
debe55
@@ -73,7 +73,12 @@ static bool OpenLibrary()
debe55
 
debe55
     if (libssl == NULL)
debe55
     {
debe55
-        // Prefer OpenSSL 1.1.x
debe55
+        // Prefer OpenSSL 3.x
debe55
+        DlOpen(MAKELIB("3"));
debe55
+    }
debe55
+
debe55
+    if (libssl == NULL)
debe55
+    {
debe55
         DlOpen(MAKELIB("1.1"));
debe55
     }
debe55
 
debe55
@@ -117,7 +122,7 @@ static void InitializeOpenSSLShim()
debe55
 #define REQUIRED_FUNCTION(fn) \
debe55
     if (!(fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn)))) { fprintf(stderr, "Cannot get required symbol " #fn " from libssl\n"); abort(); }
debe55
 
debe55
-#define NEW_REQUIRED_FUNCTION(fn) \
debe55
+#define REQUIRED_FUNCTION_110(fn) \
debe55
     if (!v1_0_sentinel && !(fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn)))) { fprintf(stderr, "Cannot get required symbol " #fn " from libssl\n"); abort(); }
debe55
 
debe55
 #define LIGHTUP_FUNCTION(fn) \
debe55
@@ -127,8 +132,8 @@ static void InitializeOpenSSLShim()
debe55
     if (!(fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn)))) { fn##_ptr = (__typeof(fn))local_##fn; }
debe55
 
debe55
 #define RENAMED_FUNCTION(fn,oldfn) \
debe55
-    if (!v1_0_sentinel && !(fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn)))) { fprintf(stderr, "Cannot get required symbol " #fn " from libssl\n"); abort(); } \
debe55
-    if (v1_0_sentinel && !(fn##_ptr = (__typeof(fn))(dlsym(libssl, #oldfn)))) { fprintf(stderr, "Cannot get required symbol " #oldfn " from libssl\n"); abort(); }
debe55
+    fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn));\
debe55
+    if (!fn##_ptr && !(fn##_ptr = (__typeof(fn))(dlsym(libssl, #oldfn)))) { fprintf(stderr, "Cannot get required symbol " #oldfn " from libssl\n"); abort(); }
debe55
 
debe55
 #define LEGACY_FUNCTION(fn) \
debe55
     if (v1_0_sentinel && !(fn##_ptr = (__typeof(fn))(dlsym(libssl, #fn)))) { fprintf(stderr, "Cannot get required symbol " #fn " from libssl\n"); abort(); }
debe55
@@ -138,8 +143,18 @@ static void InitializeOpenSSLShim()
debe55
 #undef RENAMED_FUNCTION
debe55
 #undef FALLBACK_FUNCTION
debe55
 #undef LIGHTUP_FUNCTION
debe55
-#undef NEW_REQUIRED_FUNCTION
debe55
+#undef REQUIRED_FUNCTION_110
debe55
 #undef REQUIRED_FUNCTION
debe55
+
debe55
+    // Sanity check that we have at least one functioning way of reporting errors.
debe55
+    if (ERR_put_error_ptr == &local_ERR_put_error)
debe55
+    {
debe55
+        if (ERR_new_ptr == NULL || ERR_set_debug_ptr == NULL || ERR_set_error_ptr == NULL)
debe55
+        {
debe55
+            fprintf(stderr, "Cannot determine the error reporting routine from libssl\n");
debe55
+            abort();
debe55
+        }
debe55
+    }
debe55
 }
debe55
 
debe55
 __attribute__((destructor))
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.h b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.h
debe55
index 4c15914d25..1dc9a8c35c 100644
debe55
--- a/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.h
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/opensslshim.h
debe55
@@ -36,6 +36,7 @@
debe55
 #include <openssl/x509v3.h>
debe55
 
debe55
 #include "pal_crypto_config.h"
debe55
+#define OPENSSL_VERSION_3_0_RTM 0x30000000L
debe55
 #define OPENSSL_VERSION_1_1_1_RTM 0x10101000L
debe55
 #define OPENSSL_VERSION_1_1_0_RTM 0x10100000L
debe55
 #define OPENSSL_VERSION_1_0_2_RTM 0x10002000L
debe55
@@ -64,6 +65,22 @@
debe55
 #undef SSLv23_method
debe55
 #endif
debe55
 
debe55
+#ifdef ERR_put_error
debe55
+#undef ERR_put_error
debe55
+void ERR_put_error(int32_t lib, int32_t func, int32_t reason, const char* file, int32_t line);
debe55
+#endif
debe55
+
debe55
+// The value -1 has the correct meaning on 1.0.x, but the constant wasn't named.
debe55
+#ifndef RSA_PSS_SALTLEN_DIGEST
debe55
+#define RSA_PSS_SALTLEN_DIGEST -1
debe55
+#endif
debe55
+
debe55
+#if defined FEATURE_DISTRO_AGNOSTIC_SSL || OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_3_0_RTM
debe55
+#include "apibridge_30_rev.h"
debe55
+#endif
debe55
+#if defined FEATURE_DISTRO_AGNOSTIC_SSL || OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_3_0_RTM
debe55
+#include "apibridge_30.h"
debe55
+#endif
debe55
 #if defined FEATURE_DISTRO_AGNOSTIC_SSL || OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_1_0_RTM
debe55
 #include "apibridge.h"
debe55
 #endif
debe55
@@ -72,6 +89,7 @@
debe55
 
debe55
 #define NEED_OPENSSL_1_0 true
debe55
 #define NEED_OPENSSL_1_1 true
debe55
+#define NEED_OPENSSL_3_0 true
debe55
 
debe55
 #if !HAVE_OPENSSL_EC2M
debe55
 // In portable build, we need to support the following functions even if they were not present
debe55
@@ -93,110 +111,16 @@ int SSL_CTX_set_ciphersuites(SSL_CTX *ctx, const char *str);
debe55
 const SSL_CIPHER* SSL_CIPHER_find(SSL *ssl, const unsigned char *ptr);
debe55
 #endif
debe55
 
debe55
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_1_1_0_RTM
debe55
-typedef struct stack_st _STACK;
debe55
-int CRYPTO_add_lock(int* pointer, int amount, int type, const char* file, int line);
debe55
-int CRYPTO_num_locks(void);
debe55
-void CRYPTO_set_locking_callback(void (*func)(int mode, int type, const char* file, int line));
debe55
-void ERR_load_crypto_strings(void);
debe55
-int EVP_CIPHER_CTX_cleanup(EVP_CIPHER_CTX* a);
debe55
-int EVP_CIPHER_CTX_init(EVP_CIPHER_CTX* a);
debe55
-void HMAC_CTX_cleanup(HMAC_CTX* ctx);
debe55
-void HMAC_CTX_init(HMAC_CTX* ctx);
debe55
-void OPENSSL_add_all_algorithms_conf(void);
debe55
-int SSL_library_init(void);
debe55
-void SSL_load_error_strings(void);
debe55
-int SSL_state(const SSL* ssl);
debe55
-unsigned long SSLeay(void);
debe55
+#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_3_0_RTM
debe55
+#include "osslcompat_102.h"
debe55
+#elif OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_1_1_0_RTM
debe55
+#include "osslcompat_30.h"
debe55
+#include "osslcompat_102.h"
debe55
 #else
debe55
-typedef struct ossl_init_settings_st OPENSSL_INIT_SETTINGS;
debe55
-typedef struct stack_st OPENSSL_STACK;
debe55
-
debe55
-#define OPENSSL_INIT_LOAD_CRYPTO_STRINGS 0x00000002L
debe55
-#define OPENSSL_INIT_ADD_ALL_CIPHERS 0x00000004L
debe55
-#define OPENSSL_INIT_ADD_ALL_DIGESTS 0x00000008L
debe55
-#define OPENSSL_INIT_LOAD_CONFIG 0x00000040L
debe55
-#define OPENSSL_INIT_LOAD_SSL_STRINGS 0x00200000L
debe55
-
debe55
-const BIGNUM* DSA_get0_key(const DSA* dsa, const BIGNUM** pubKey, const BIGNUM** privKey);
debe55
-void DSA_get0_pqg(const DSA* dsa, const BIGNUM** p, const BIGNUM** q, const BIGNUM** g);
debe55
-const DSA_METHOD* DSA_get_method(const DSA* dsa);
debe55
-int32_t DSA_set0_key(DSA* dsa, BIGNUM* bnY, BIGNUM* bnX);
debe55
-int32_t DSA_set0_pqg(DSA* dsa, BIGNUM* bnP, BIGNUM* bnQ, BIGNUM* bnG);
debe55
-void EVP_CIPHER_CTX_free(EVP_CIPHER_CTX* ctx);
debe55
-EVP_CIPHER_CTX* EVP_CIPHER_CTX_new(void);
debe55
-int32_t EVP_CIPHER_CTX_reset(EVP_CIPHER_CTX* ctx);
debe55
-void EVP_MD_CTX_free(EVP_MD_CTX* ctx);
debe55
-EVP_MD_CTX* EVP_MD_CTX_new(void);
debe55
-RSA* EVP_PKEY_get0_RSA(EVP_PKEY* pkey);
debe55
-int32_t EVP_PKEY_up_ref(EVP_PKEY* pkey);
debe55
-void HMAC_CTX_free(HMAC_CTX* ctx);
debe55
-HMAC_CTX* HMAC_CTX_new(void);
debe55
-int OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS* settings);
debe55
-void OPENSSL_sk_free(OPENSSL_STACK*);
debe55
-OPENSSL_STACK* OPENSSL_sk_new_null(void);
debe55
-int OPENSSL_sk_num(const OPENSSL_STACK*);
debe55
-void* OPENSSL_sk_pop(OPENSSL_STACK* st);
debe55
-void OPENSSL_sk_pop_free(OPENSSL_STACK* st, void (*func)(void*));
debe55
-int OPENSSL_sk_push(OPENSSL_STACK* st, const void* data);
debe55
-void* OPENSSL_sk_value(const OPENSSL_STACK*, int);
debe55
-long OpenSSL_version_num(void);
debe55
-void RSA_get0_crt_params(const RSA* rsa, const BIGNUM** dmp1, const BIGNUM** dmq1, const BIGNUM** iqmp);
debe55
-void RSA_get0_factors(const RSA* rsa, const BIGNUM** p, const BIGNUM** q);
debe55
-void RSA_get0_key(const RSA* rsa, const BIGNUM** n, const BIGNUM** e, const BIGNUM** d);
debe55
-int32_t RSA_meth_get_flags(const RSA_METHOD* meth);
debe55
-const RSA_METHOD* RSA_PKCS1_OpenSSL(void);
debe55
-int32_t RSA_pkey_ctx_ctrl(EVP_PKEY_CTX* ctx, int32_t optype, int32_t cmd, int32_t p1, void* p2);
debe55
-int32_t RSA_set0_crt_params(RSA* rsa, BIGNUM* dmp1, BIGNUM* dmq1, BIGNUM* iqmp);
debe55
-int32_t RSA_set0_factors(RSA* rsa, BIGNUM* p, BIGNUM* q);
debe55
-int32_t RSA_set0_key(RSA* rsa, BIGNUM* n, BIGNUM* e, BIGNUM* d);
debe55
-int32_t SSL_is_init_finished(SSL* ssl);
debe55
-#undef SSL_CTX_set_options
debe55
-unsigned long SSL_CTX_set_options(SSL_CTX* ctx, unsigned long options);
debe55
-void SSL_CTX_set_security_level(SSL_CTX* ctx, int32_t level);
debe55
-#undef SSL_session_reused
debe55
-int SSL_session_reused(SSL* ssl);
debe55
-const SSL_METHOD* TLS_method(void);
debe55
-const ASN1_TIME* X509_CRL_get0_nextUpdate(const X509_CRL* crl);
debe55
-int32_t X509_NAME_get0_der(X509_NAME* x509Name, const uint8_t** pder, size_t* pderlen);
debe55
-int32_t X509_PUBKEY_get0_param(
debe55
-    ASN1_OBJECT** palgOid, const uint8_t** pkeyBytes, int* pkeyBytesLen, X509_ALGOR** palg, X509_PUBKEY* pubkey);
debe55
-X509* X509_STORE_CTX_get0_cert(X509_STORE_CTX* ctx);
debe55
-STACK_OF(X509)* X509_STORE_CTX_get0_chain(X509_STORE_CTX* ctx);
debe55
-STACK_OF(X509)* X509_STORE_CTX_get0_untrusted(X509_STORE_CTX* ctx);
debe55
-X509_VERIFY_PARAM* X509_STORE_get0_param(X509_STORE* ctx);
debe55
-const ASN1_TIME* X509_get0_notAfter(const X509* x509);
debe55
-const ASN1_TIME* X509_get0_notBefore(const X509* x509);
debe55
-ASN1_BIT_STRING* X509_get0_pubkey_bitstr(const X509* x509);
debe55
-const X509_ALGOR* X509_get0_tbs_sigalg(const X509* x509);
debe55
-X509_PUBKEY* X509_get_X509_PUBKEY(const X509* x509);
debe55
-int32_t X509_get_version(const X509* x509);
debe55
-int32_t X509_up_ref(X509* x509);
debe55
-
debe55
-// Redefine EVP_PKEY_CTX_set_rsa operations to use (local_)RSA_pkey_ctx_ctrl so the path is the same
debe55
-// for 1.0-built on 1.1 as on 1.1-built on 1.1.
debe55
-#undef EVP_PKEY_CTX_set_rsa_keygen_bits
debe55
-#define EVP_PKEY_CTX_set_rsa_keygen_bits(ctx, bits) \
debe55
-    RSA_pkey_ctx_ctrl(ctx, EVP_PKEY_OP_KEYGEN, EVP_PKEY_CTRL_RSA_KEYGEN_BITS, bits, NULL)
debe55
-
debe55
-// EVP_PKEY_CTX_set_rsa_oaep_md doesn't call RSA_pkey_ctx_ctrl in 1.1, so don't redefine it here.
debe55
-
debe55
-#undef EVP_PKEY_CTX_set_rsa_padding
debe55
-#define EVP_PKEY_CTX_set_rsa_padding(ctx, pad) \
debe55
-    RSA_pkey_ctx_ctrl(ctx, -1, EVP_PKEY_CTRL_RSA_PADDING, pad, NULL)
debe55
-
debe55
-#undef EVP_PKEY_CTX_set_rsa_pss_saltlen
debe55
-#define EVP_PKEY_CTX_set_rsa_pss_saltlen(ctx, len) \
debe55
-    RSA_pkey_ctx_ctrl(ctx, (EVP_PKEY_OP_SIGN|EVP_PKEY_OP_VERIFY), EVP_PKEY_CTRL_RSA_PSS_SALTLEN, len, NULL)
debe55
-
debe55
+#include "osslcompat_30.h"
debe55
+#include "osslcompat_111.h"
debe55
 #endif
debe55
 
debe55
-#if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_0_2_RTM
debe55
-X509_STORE* X509_STORE_CTX_get0_store(X509_STORE_CTX* ctx);
debe55
-int32_t X509_check_host(X509* x509, const char* name, size_t namelen, unsigned int flags, char** peername);
debe55
-#define X509_CHECK_FLAG_NO_PARTIAL_WILDCARDS 4
debe55
-
debe55
-#endif
debe55
 
debe55
 #if !HAVE_OPENSSL_ALPN
debe55
 #undef HAVE_OPENSSL_ALPN
debe55
@@ -213,11 +137,6 @@ void SSL_CTX_set_alpn_select_cb(SSL_CTX* ctx,
debe55
 void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsigned int* len);
debe55
 #endif
debe55
 
debe55
-// The value -1 has the correct meaning on 1.0.x, but the constant wasn't named.
debe55
-#ifndef RSA_PSS_SALTLEN_DIGEST
debe55
-#define RSA_PSS_SALTLEN_DIGEST -1
debe55
-#endif
debe55
-
debe55
 #define API_EXISTS(fn) (fn != NULL)
debe55
 
debe55
 // List of all functions from the libssl that are used in the System.Security.Cryptography.Native.
debe55
@@ -326,10 +245,13 @@ void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsi
debe55
     REQUIRED_FUNCTION(ERR_error_string_n) \
debe55
     REQUIRED_FUNCTION(ERR_get_error) \
debe55
     LEGACY_FUNCTION(ERR_load_crypto_strings) \
debe55
-    REQUIRED_FUNCTION(ERR_put_error) \
debe55
+    LIGHTUP_FUNCTION(ERR_new) \
debe55
     REQUIRED_FUNCTION(ERR_peek_error) \
debe55
     REQUIRED_FUNCTION(ERR_peek_last_error) \
debe55
+    FALLBACK_FUNCTION(ERR_put_error) \
debe55
     REQUIRED_FUNCTION(ERR_reason_error_string) \
debe55
+    LIGHTUP_FUNCTION(ERR_set_debug) \
debe55
+    LIGHTUP_FUNCTION(ERR_set_error) \
debe55
     REQUIRED_FUNCTION(EVP_aes_128_cbc) \
debe55
     REQUIRED_FUNCTION(EVP_aes_128_ccm) \
debe55
     REQUIRED_FUNCTION(EVP_aes_128_ecb) \
debe55
@@ -370,6 +292,11 @@ void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsi
debe55
     REQUIRED_FUNCTION(EVP_PKEY_CTX_get0_pkey) \
debe55
     REQUIRED_FUNCTION(EVP_PKEY_CTX_new) \
debe55
     REQUIRED_FUNCTION(EVP_PKEY_CTX_new_id) \
debe55
+    FALLBACK_FUNCTION(EVP_PKEY_CTX_set_rsa_keygen_bits) \
debe55
+    FALLBACK_FUNCTION(EVP_PKEY_CTX_set_rsa_oaep_md) \
debe55
+    FALLBACK_FUNCTION(EVP_PKEY_CTX_set_rsa_padding) \
debe55
+    FALLBACK_FUNCTION(EVP_PKEY_CTX_set_rsa_pss_saltlen) \
debe55
+    FALLBACK_FUNCTION(EVP_PKEY_CTX_set_signature_md) \
debe55
     REQUIRED_FUNCTION(EVP_PKEY_base_id) \
debe55
     REQUIRED_FUNCTION(EVP_PKEY_decrypt) \
debe55
     REQUIRED_FUNCTION(EVP_PKEY_decrypt_init) \
debe55
@@ -438,7 +365,7 @@ void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsi
debe55
     REQUIRED_FUNCTION(OCSP_RESPONSE_new) \
debe55
     LEGACY_FUNCTION(OPENSSL_add_all_algorithms_conf) \
debe55
     REQUIRED_FUNCTION(OPENSSL_cleanse) \
debe55
-    NEW_REQUIRED_FUNCTION(OPENSSL_init_ssl) \
debe55
+    REQUIRED_FUNCTION_110(OPENSSL_init_ssl) \
debe55
     RENAMED_FUNCTION(OPENSSL_sk_free, sk_free) \
debe55
     RENAMED_FUNCTION(OPENSSL_sk_new_null, sk_new_null) \
debe55
     RENAMED_FUNCTION(OPENSSL_sk_num, sk_num) \
debe55
@@ -510,11 +437,11 @@ void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsi
debe55
     REQUIRED_FUNCTION(SSL_get_error) \
debe55
     REQUIRED_FUNCTION(SSL_get_finished) \
debe55
     REQUIRED_FUNCTION(SSL_get_peer_cert_chain) \
debe55
-    REQUIRED_FUNCTION(SSL_get_peer_certificate) \
debe55
     REQUIRED_FUNCTION(SSL_get_peer_finished) \
debe55
     REQUIRED_FUNCTION(SSL_get_SSL_CTX) \
debe55
     REQUIRED_FUNCTION(SSL_get_version) \
debe55
     LIGHTUP_FUNCTION(SSL_get0_alpn_selected) \
debe55
+    RENAMED_FUNCTION(SSL_get1_peer_certificate, SSL_get_peer_certificate) \
debe55
     LEGACY_FUNCTION(SSL_library_init) \
debe55
     LEGACY_FUNCTION(SSL_load_error_strings) \
debe55
     REQUIRED_FUNCTION(SSL_new) \
debe55
@@ -606,7 +533,7 @@ void SSL_get0_alpn_selected(const SSL* ssl, const unsigned char** protocol, unsi
debe55
 
debe55
 // Declare pointers to all the used OpenSSL functions
debe55
 #define REQUIRED_FUNCTION(fn) extern __typeof(fn)* fn##_ptr;
debe55
-#define NEW_REQUIRED_FUNCTION(fn) extern __typeof(fn)* fn##_ptr;
debe55
+#define REQUIRED_FUNCTION_110(fn) extern __typeof(fn)* fn##_ptr;
debe55
 #define LIGHTUP_FUNCTION(fn) extern __typeof(fn)* fn##_ptr;
debe55
 #define FALLBACK_FUNCTION(fn) extern __typeof(fn)* fn##_ptr;
debe55
 #define RENAMED_FUNCTION(fn,oldfn) extern __typeof(fn)* fn##_ptr;
debe55
@@ -616,7 +543,7 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #undef RENAMED_FUNCTION
debe55
 #undef FALLBACK_FUNCTION
debe55
 #undef LIGHTUP_FUNCTION
debe55
-#undef NEW_REQUIRED_FUNCTION
debe55
+#undef REQUIRED_FUNCTION_110
debe55
 #undef REQUIRED_FUNCTION
debe55
 
debe55
 // Redefine all calls to OpenSSL functions as calls through pointers that are set
debe55
@@ -722,10 +649,13 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define ERR_error_string_n ERR_error_string_n_ptr
debe55
 #define ERR_get_error ERR_get_error_ptr
debe55
 #define ERR_load_crypto_strings ERR_load_crypto_strings_ptr
debe55
+#define ERR_new ERR_new_ptr
debe55
 #define ERR_peek_error ERR_peek_error_ptr
debe55
 #define ERR_peek_last_error ERR_peek_last_error_ptr
debe55
 #define ERR_put_error ERR_put_error_ptr
debe55
 #define ERR_reason_error_string ERR_reason_error_string_ptr
debe55
+#define ERR_set_debug ERR_set_debug_ptr
debe55
+#define ERR_set_error ERR_set_error_ptr
debe55
 #define EVP_aes_128_cbc EVP_aes_128_cbc_ptr
debe55
 #define EVP_aes_128_ecb EVP_aes_128_ecb_ptr
debe55
 #define EVP_aes_128_gcm EVP_aes_128_gcm_ptr
debe55
@@ -766,6 +696,11 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define EVP_PKEY_CTX_get0_pkey EVP_PKEY_CTX_get0_pkey_ptr
debe55
 #define EVP_PKEY_CTX_new EVP_PKEY_CTX_new_ptr
debe55
 #define EVP_PKEY_CTX_new_id EVP_PKEY_CTX_new_id_ptr
debe55
+#define EVP_PKEY_CTX_set_rsa_keygen_bits EVP_PKEY_CTX_set_rsa_keygen_bits_ptr
debe55
+#define EVP_PKEY_CTX_set_rsa_oaep_md EVP_PKEY_CTX_set_rsa_oaep_md_ptr
debe55
+#define EVP_PKEY_CTX_set_rsa_padding EVP_PKEY_CTX_set_rsa_padding_ptr
debe55
+#define EVP_PKEY_CTX_set_rsa_pss_saltlen EVP_PKEY_CTX_set_rsa_pss_saltlen_ptr
debe55
+#define EVP_PKEY_CTX_set_signature_md EVP_PKEY_CTX_set_signature_md_ptr
debe55
 #define EVP_PKEY_base_id EVP_PKEY_base_id_ptr
debe55
 #define EVP_PKEY_decrypt_init EVP_PKEY_decrypt_init_ptr
debe55
 #define EVP_PKEY_decrypt EVP_PKEY_decrypt_ptr
debe55
@@ -875,13 +810,6 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define RSA_size RSA_size_ptr
debe55
 #define RSA_up_ref RSA_up_ref_ptr
debe55
 #define RSA_verify RSA_verify_ptr
debe55
-#define sk_free OPENSSL_sk_free_ptr
debe55
-#define sk_new_null OPENSSL_sk_new_null_ptr
debe55
-#define sk_num OPENSSL_sk_num_ptr
debe55
-#define sk_pop OPENSSL_sk_pop_ptr
debe55
-#define sk_pop_free OPENSSL_sk_pop_free_ptr
debe55
-#define sk_push OPENSSL_sk_push_ptr
debe55
-#define sk_value OPENSSL_sk_value_ptr
debe55
 #define SSL_CIPHER_get_bits SSL_CIPHER_get_bits_ptr
debe55
 #define SSL_CIPHER_find SSL_CIPHER_find_ptr
debe55
 #define SSL_CIPHER_get_id SSL_CIPHER_get_id_ptr
debe55
@@ -912,11 +840,11 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define SSL_get_error SSL_get_error_ptr
debe55
 #define SSL_get_finished SSL_get_finished_ptr
debe55
 #define SSL_get_peer_cert_chain SSL_get_peer_cert_chain_ptr
debe55
-#define SSL_get_peer_certificate SSL_get_peer_certificate_ptr
debe55
 #define SSL_get_peer_finished SSL_get_peer_finished_ptr
debe55
 #define SSL_get_SSL_CTX SSL_get_SSL_CTX_ptr
debe55
 #define SSL_get_version SSL_get_version_ptr
debe55
 #define SSL_get0_alpn_selected SSL_get0_alpn_selected_ptr
debe55
+#define SSL_get1_peer_certificate SSL_get1_peer_certificate_ptr
debe55
 #define SSL_is_init_finished SSL_is_init_finished_ptr
debe55
 #define SSL_library_init SSL_library_init_ptr
debe55
 #define SSL_load_error_strings SSL_load_error_strings_ptr
debe55
@@ -1011,7 +939,7 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 // STACK_OF types will have been declared with inline functions to handle the pointer casting.
debe55
 // Since these inline functions are strongly bound to the OPENSSL_sk_* functions in 1.1 we need to
debe55
 // rebind things here.
debe55
-#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_1_1_0_RTM
debe55
+#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_1_1_0_RTM && OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_3_0_RTM
debe55
 // type-safe OPENSSL_sk_free
debe55
 #define sk_GENERAL_NAME_free(stack) OPENSSL_sk_free((OPENSSL_STACK*)(1 ? stack : (STACK_OF(GENERAL_NAME)*)0))
debe55
 #define sk_X509_free(stack) OPENSSL_sk_free((OPENSSL_STACK*)(1 ? stack : (STACK_OF(X509)*)0))
debe55
@@ -1039,6 +967,17 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define sk_GENERAL_NAME_value(stack, idx) (GENERAL_NAME*)OPENSSL_sk_value((const OPENSSL_STACK*)(1 ? stack : (const STACK_OF(GENERAL_NAME)*)0), idx)
debe55
 #define sk_X509_NAME_value(stack, idx) (X509_NAME*)OPENSSL_sk_value((const OPENSSL_STACK*)(1 ? stack : (const STACK_OF(X509_NAME)*)0), idx)
debe55
 #define sk_X509_value(stack, idx) (X509*)OPENSSL_sk_value((const OPENSSL_STACK*)(1 ? stack : (const STACK_OF(X509)*)0), idx)
debe55
+
debe55
+#elif OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_1_0_RTM
debe55
+
debe55
+#define sk_free OPENSSL_sk_free_ptr
debe55
+#define sk_new_null OPENSSL_sk_new_null_ptr
debe55
+#define sk_num OPENSSL_sk_num_ptr
debe55
+#define sk_pop OPENSSL_sk_pop_ptr
debe55
+#define sk_pop_free OPENSSL_sk_pop_free_ptr
debe55
+#define sk_push OPENSSL_sk_push_ptr
debe55
+#define sk_value OPENSSL_sk_value_ptr
debe55
+
debe55
 #endif
debe55
 
debe55
 
debe55
@@ -1046,9 +985,26 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 
debe55
 #define API_EXISTS(fn) true
debe55
 
debe55
-#if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_1_0_RTM
debe55
-
debe55
+#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_3_0_RTM
debe55
+#define NEED_OPENSSL_3_0 true
debe55
+#elif OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_1_1_0_RTM
debe55
+#define NEED_OPENSSL_1_1 true
debe55
+#else
debe55
 #define NEED_OPENSSL_1_0 true
debe55
+#endif
debe55
+
debe55
+#if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_3_0_RTM
debe55
+
debe55
+// Undo renames for renamed-in-3.0
debe55
+#define SSL_get1_peer_certificate SSL_get_peer_certificate
debe55
+
debe55
+#endif
debe55
+
debe55
+#if OPENSSL_VERSION_NUMBER >= OPENSSL_VERSION_3_0_RTM
debe55
+
debe55
+#define ERR_put_error local_ERR_put_error
debe55
+
debe55
+#elif OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_1_0_RTM
debe55
 
debe55
 // Alias "future" API to the local_ version.
debe55
 #define DSA_get0_key local_DSA_get0_key
debe55
@@ -1110,10 +1066,6 @@ FOR_ALL_OPENSSL_FUNCTIONS
debe55
 #define OPENSSL_sk_value sk_value
debe55
 #define TLS_method SSLv23_method
debe55
 
debe55
-#else // if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_1_0_RTM
debe55
-
debe55
-#define NEED_OPENSSL_1_1 true
debe55
-
debe55
 #endif
debe55
 
debe55
 #endif // FEATURE_DISTRO_AGNOSTIC_SSL
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_102.h b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_102.h
debe55
new file mode 100644
debe55
index 0000000000..2ee440c320
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_102.h
debe55
@@ -0,0 +1,34 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+//
debe55
+
debe55
+#pragma once
debe55
+
debe55
+// Function prototypes unique to OpenSSL 1.0.2
debe55
+
debe55
+typedef struct stack_st _STACK;
debe55
+
debe55
+#undef CRYPTO_num_locks
debe55
+#undef CRYPTO_set_locking_callback
debe55
+#undef ERR_load_crypto_strings
debe55
+#undef EVP_CIPHER_CTX_cleanup
debe55
+#undef EVP_CIPHER_CTX_init
debe55
+#undef OPENSSL_add_all_algorithms_conf
debe55
+#undef SSL_library_init
debe55
+#undef SSL_load_error_strings
debe55
+#undef SSL_state
debe55
+#undef SSLeay
debe55
+
debe55
+int CRYPTO_add_lock(int* pointer, int amount, int type, const char* file, int line);
debe55
+int CRYPTO_num_locks(void);
debe55
+void CRYPTO_set_locking_callback(void (*func)(int mode, int type, const char* file, int line));
debe55
+void ERR_load_crypto_strings(void);
debe55
+int EVP_CIPHER_CTX_cleanup(EVP_CIPHER_CTX* a);
debe55
+int EVP_CIPHER_CTX_init(EVP_CIPHER_CTX* a);
debe55
+void HMAC_CTX_cleanup(HMAC_CTX* ctx);
debe55
+void HMAC_CTX_init(HMAC_CTX* ctx);
debe55
+void OPENSSL_add_all_algorithms_conf(void);
debe55
+int SSL_library_init(void);
debe55
+void SSL_load_error_strings(void);
debe55
+int SSL_state(const SSL* ssl);
debe55
+unsigned long SSLeay(void);
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_111.h b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_111.h
debe55
new file mode 100644
debe55
index 0000000000..0a730cef89
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_111.h
debe55
@@ -0,0 +1,80 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+
debe55
+// Function prototypes unique to OpenSSL 1.1.x
debe55
+
debe55
+#pragma once
debe55
+#include "pal_types.h"
debe55
+
debe55
+#undef SSL_CTX_set_options
debe55
+#undef SSL_session_reused
debe55
+
debe55
+typedef struct ossl_init_settings_st OPENSSL_INIT_SETTINGS;
debe55
+typedef struct stack_st OPENSSL_STACK;
debe55
+
debe55
+#define OPENSSL_INIT_LOAD_CRYPTO_STRINGS 0x00000002L
debe55
+#define OPENSSL_INIT_ADD_ALL_CIPHERS 0x00000004L
debe55
+#define OPENSSL_INIT_ADD_ALL_DIGESTS 0x00000008L
debe55
+#define OPENSSL_INIT_LOAD_CONFIG 0x00000040L
debe55
+#define OPENSSL_INIT_LOAD_SSL_STRINGS 0x00200000L
debe55
+
debe55
+const BIGNUM* DSA_get0_key(const DSA* dsa, const BIGNUM** pubKey, const BIGNUM** privKey);
debe55
+void DSA_get0_pqg(const DSA* dsa, const BIGNUM** p, const BIGNUM** q, const BIGNUM** g);
debe55
+const DSA_METHOD* DSA_get_method(const DSA* dsa);
debe55
+int32_t DSA_set0_key(DSA* dsa, BIGNUM* bnY, BIGNUM* bnX);
debe55
+int32_t DSA_set0_pqg(DSA* dsa, BIGNUM* bnP, BIGNUM* bnQ, BIGNUM* bnG);
debe55
+void EVP_CIPHER_CTX_free(EVP_CIPHER_CTX* ctx);
debe55
+EVP_CIPHER_CTX* EVP_CIPHER_CTX_new(void);
debe55
+int32_t EVP_CIPHER_CTX_reset(EVP_CIPHER_CTX* ctx);
debe55
+void EVP_MD_CTX_free(EVP_MD_CTX* ctx);
debe55
+EVP_MD_CTX* EVP_MD_CTX_new(void);
debe55
+RSA* EVP_PKEY_get0_RSA(EVP_PKEY* pkey);
debe55
+int32_t EVP_PKEY_up_ref(EVP_PKEY* pkey);
debe55
+void HMAC_CTX_free(HMAC_CTX* ctx);
debe55
+HMAC_CTX* HMAC_CTX_new(void);
debe55
+int OPENSSL_init_ssl(uint64_t opts, const OPENSSL_INIT_SETTINGS* settings);
debe55
+void OPENSSL_sk_free(OPENSSL_STACK*);
debe55
+OPENSSL_STACK* OPENSSL_sk_new_null(void);
debe55
+int OPENSSL_sk_num(const OPENSSL_STACK*);
debe55
+void* OPENSSL_sk_pop(OPENSSL_STACK* st);
debe55
+void OPENSSL_sk_pop_free(OPENSSL_STACK* st, void (*func)(void*));
debe55
+int OPENSSL_sk_push(OPENSSL_STACK* st, const void* data);
debe55
+void* OPENSSL_sk_value(const OPENSSL_STACK*, int);
debe55
+long OpenSSL_version_num(void);
debe55
+const RSA_METHOD* RSA_PKCS1_OpenSSL(void);
debe55
+void RSA_get0_crt_params(const RSA* rsa, const BIGNUM** dmp1, const BIGNUM** dmq1, const BIGNUM** iqmp);
debe55
+void RSA_get0_factors(const RSA* rsa, const BIGNUM** p, const BIGNUM** q);
debe55
+void RSA_get0_key(const RSA* rsa, const BIGNUM** n, const BIGNUM** e, const BIGNUM** d);
debe55
+int32_t RSA_meth_get_flags(const RSA_METHOD* meth);
debe55
+int32_t RSA_pkey_ctx_ctrl(EVP_PKEY_CTX* ctx, int32_t optype, int32_t cmd, int32_t p1, void* p2);
debe55
+int32_t RSA_set0_crt_params(RSA* rsa, BIGNUM* dmp1, BIGNUM* dmq1, BIGNUM* iqmp);
debe55
+int32_t RSA_set0_factors(RSA* rsa, BIGNUM* p, BIGNUM* q);
debe55
+int32_t RSA_set0_key(RSA* rsa, BIGNUM* n, BIGNUM* e, BIGNUM* d);
debe55
+int SSL_CTX_config(SSL_CTX* ctx, const char* name);
debe55
+unsigned long SSL_CTX_set_options(SSL_CTX* ctx, unsigned long options);
debe55
+void SSL_CTX_set_security_level(SSL_CTX* ctx, int32_t level);
debe55
+int32_t SSL_is_init_finished(SSL* ssl);
debe55
+int SSL_session_reused(SSL* ssl);
debe55
+const SSL_METHOD* TLS_method(void);
debe55
+const ASN1_TIME* X509_CRL_get0_nextUpdate(const X509_CRL* crl);
debe55
+int32_t X509_NAME_get0_der(X509_NAME* x509Name, const uint8_t** pder, size_t* pderlen);
debe55
+int32_t X509_PUBKEY_get0_param(
debe55
+    ASN1_OBJECT** palgOid, const uint8_t** pkeyBytes, int* pkeyBytesLen, X509_ALGOR** palg, X509_PUBKEY* pubkey);
debe55
+X509* X509_STORE_CTX_get0_cert(X509_STORE_CTX* ctx);
debe55
+STACK_OF(X509) * X509_STORE_CTX_get0_chain(X509_STORE_CTX* ctx);
debe55
+STACK_OF(X509) * X509_STORE_CTX_get0_untrusted(X509_STORE_CTX* ctx);
debe55
+X509_VERIFY_PARAM* X509_STORE_get0_param(X509_STORE* ctx);
debe55
+const ASN1_TIME* X509_get0_notAfter(const X509* x509);
debe55
+const ASN1_TIME* X509_get0_notBefore(const X509* x509);
debe55
+ASN1_BIT_STRING* X509_get0_pubkey_bitstr(const X509* x509);
debe55
+const X509_ALGOR* X509_get0_tbs_sigalg(const X509* x509);
debe55
+X509_PUBKEY* X509_get_X509_PUBKEY(const X509* x509);
debe55
+int32_t X509_get_version(const X509* x509);
debe55
+int32_t X509_up_ref(X509* x509);
debe55
+
debe55
+#if OPENSSL_VERSION_NUMBER < OPENSSL_VERSION_1_0_2_RTM
debe55
+int32_t X509_check_host(X509* x509, const char* name, size_t namelen, unsigned int flags, char** peername);
debe55
+X509_STORE* X509_STORE_CTX_get0_store(X509_STORE_CTX* ctx);
debe55
+#define X509_CHECK_FLAG_NO_PARTIAL_WILDCARDS 4
debe55
+
debe55
+#endif
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_30.h b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_30.h
debe55
new file mode 100644
debe55
index 0000000000..0fe57c9132
debe55
--- /dev/null
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/osslcompat_30.h
debe55
@@ -0,0 +1,23 @@
debe55
+// Licensed to the .NET Foundation under one or more agreements.
debe55
+// The .NET Foundation licenses this file to you under the MIT license.
debe55
+
debe55
+// Function prototypes unique to OpenSSL 3.0
debe55
+
debe55
+#pragma once
debe55
+#include "pal_types.h"
debe55
+
debe55
+#undef EVP_PKEY_CTX_set_rsa_keygen_bits
debe55
+#undef EVP_PKEY_CTX_set_rsa_oaep_md
debe55
+#undef EVP_PKEY_CTX_set_rsa_padding
debe55
+#undef EVP_PKEY_CTX_set_rsa_pss_saltlen
debe55
+#undef EVP_PKEY_CTX_set_signature_md
debe55
+
debe55
+void ERR_new(void);
debe55
+void ERR_set_debug(const char *file, int line, const char *func);
debe55
+void ERR_set_error(int lib, int reason, const char *fmt, ...);
debe55
+int EVP_PKEY_CTX_set_rsa_keygen_bits(EVP_PKEY_CTX* ctx, int bits);
debe55
+int EVP_PKEY_CTX_set_rsa_oaep_md(EVP_PKEY_CTX* ctx, const EVP_MD* md);
debe55
+int EVP_PKEY_CTX_set_rsa_padding(EVP_PKEY_CTX* ctx, int pad_mode);
debe55
+int EVP_PKEY_CTX_set_rsa_pss_saltlen(EVP_PKEY_CTX* ctx, int saltlen);
debe55
+int EVP_PKEY_CTX_set_signature_md(EVP_PKEY_CTX* ctx, const EVP_MD* md);
debe55
+X509* SSL_get1_peer_certificate(const SSL* ssl);
debe55
diff --git a/src/Native/Unix/System.Security.Cryptography.Native/pal_ssl.c b/src/Native/Unix/System.Security.Cryptography.Native/pal_ssl.c
debe55
index 7764464bc8..c2e3fb2028 100644
debe55
--- a/src/Native/Unix/System.Security.Cryptography.Native/pal_ssl.c
debe55
+++ b/src/Native/Unix/System.Security.Cryptography.Native/pal_ssl.c
debe55
@@ -285,7 +285,7 @@ int32_t CryptoNative_IsSslStateOK(SSL* ssl)
debe55
 
debe55
 X509* CryptoNative_SslGetPeerCertificate(SSL* ssl)
debe55
 {
debe55
-    return SSL_get_peer_certificate(ssl);
debe55
+    return SSL_get1_peer_certificate(ssl);
debe55
 }
debe55
 
debe55
 X509Stack* CryptoNative_SslGetPeerCertChain(SSL* ssl)
debe55
-- 
debe55
2.31.1
debe55