This is an automated email from the ASF dual-hosted git repository.

remm pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/tomcat.git


The following commit(s) were added to refs/heads/main by this push:
     new ba64fe2a0b Add basic LibreSSL support
ba64fe2a0b is described below

commit ba64fe2a0bb8cf85a2554201d63a76ea6e098a3f
Author: remm <r...@apache.org>
AuthorDate: Wed Jul 3 15:08:43 2024 +0200

    Add basic LibreSSL support
    
    Client cert and similar do not appear to work ("no renegotiation" error
    seen on the client).
    Skip conf test.
    Update the MacOS default behavior using two system properties.
---
 .../util/net/openssl/panama/OpenSSLContext.java    |  35 +++----
 .../util/net/openssl/panama/OpenSSLEngine.java     |  21 +++--
 .../util/net/openssl/panama/OpenSSLLibrary.java    |   7 +-
 java/org/apache/tomcat/util/openssl/openssl_h.java |  52 +++++++++--
 .../util/openssl/openssl_h_Compatibility.java      | 101 +++++++++++++++++++++
 .../tomcat/util/net/openssl/TestOpenSSLConf.java   |   1 +
 webapps/docs/changelog.xml                         |  16 ++++
 webapps/docs/config/systemprops.xml                |  13 +++
 8 files changed, 209 insertions(+), 37 deletions(-)

diff --git a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java 
b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java
index 3dedf0fd22..e186586d78 100644
--- a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java
+++ b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java
@@ -66,6 +66,7 @@ import 
org.apache.tomcat.util.openssl.SSL_CTX_set_alpn_select_cb$cb;
 import org.apache.tomcat.util.openssl.SSL_CTX_set_cert_verify_callback$cb;
 import org.apache.tomcat.util.openssl.SSL_CTX_set_tmp_dh_callback$dh;
 import org.apache.tomcat.util.openssl.SSL_CTX_set_verify$callback;
+import org.apache.tomcat.util.openssl.openssl_h_Compatibility;
 import org.apache.tomcat.util.openssl.pem_password_cb;
 import org.apache.tomcat.util.res.StringManager;
 
@@ -135,13 +136,13 @@ public class OpenSSLContext implements 
org.apache.tomcat.util.net.SSLContext {
 
     private static String[] getCiphers(MemorySegment sslCtx) {
         MemorySegment sk = SSL_CTX_get_ciphers(sslCtx);
-        int len = OPENSSL_sk_num(sk);
+        int len = openssl_h_Compatibility.OPENSSL_sk_num(sk);
         if (len <= 0) {
             return null;
         }
         ArrayList<String> ciphers = new ArrayList<>(len);
         for (int i = 0; i < len; i++) {
-            MemorySegment cipher = OPENSSL_sk_value(sk, i);
+            MemorySegment cipher = 
openssl_h_Compatibility.OPENSSL_sk_value(sk, i);
             MemorySegment cipherName = SSL_CIPHER_get_name(cipher);
             ciphers.add(cipherName.getString(0));
         }
@@ -243,14 +244,14 @@ public class OpenSSLContext implements 
org.apache.tomcat.util.net.SSLContext {
             SSL_CTX_set_min_proto_version(sslCtx, prot);
 
             // Disable compression, usually unsafe
-            SSL_CTX_set_options(sslCtx, SSL_OP_NO_COMPRESSION());
+            openssl_h_Compatibility.SSL_CTX_set_options(sslCtx, 
SSL_OP_NO_COMPRESSION());
 
             // Disallow a session from being resumed during a renegotiation,
             // so that an acceptable cipher suite can be negotiated.
-            SSL_CTX_set_options(sslCtx, 
SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION());
+            openssl_h_Compatibility.SSL_CTX_set_options(sslCtx, 
SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION());
 
-            SSL_CTX_set_options(sslCtx, SSL_OP_SINGLE_DH_USE());
-            SSL_CTX_set_options(sslCtx, SSL_OP_SINGLE_ECDH_USE());
+            openssl_h_Compatibility.SSL_CTX_set_options(sslCtx, 
SSL_OP_SINGLE_DH_USE());
+            openssl_h_Compatibility.SSL_CTX_set_options(sslCtx, 
SSL_OP_SINGLE_ECDH_USE());
 
             // Default session context id and cache size
             SSL_CTX_sess_set_cache_size(sslCtx, 256);
@@ -463,31 +464,31 @@ public class OpenSSLContext implements 
org.apache.tomcat.util.net.SSLContext {
         boolean success = true;
         try (var localArena = Arena.ofConfined()) {
             if (sslHostConfig.getInsecureRenegotiation()) {
-                SSL_CTX_set_options(state.sslCtx, 
SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION());
+                openssl_h_Compatibility.SSL_CTX_set_options(state.sslCtx, 
SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION());
             } else {
-                SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION());
+                openssl_h_Compatibility.SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION());
             }
 
             // Use server's preference order for ciphers (rather than
             // client's)
             if (sslHostConfig.getHonorCipherOrder()) {
-                SSL_CTX_set_options(state.sslCtx, 
SSL_OP_CIPHER_SERVER_PREFERENCE());
+                openssl_h_Compatibility.SSL_CTX_set_options(state.sslCtx, 
SSL_OP_CIPHER_SERVER_PREFERENCE());
             } else {
-                SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_CIPHER_SERVER_PREFERENCE());
+                openssl_h_Compatibility.SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_CIPHER_SERVER_PREFERENCE());
             }
 
             // Disable compression if requested
             if (sslHostConfig.getDisableCompression()) {
-                SSL_CTX_set_options(state.sslCtx, SSL_OP_NO_COMPRESSION());
+                openssl_h_Compatibility.SSL_CTX_set_options(state.sslCtx, 
SSL_OP_NO_COMPRESSION());
             } else {
-                SSL_CTX_clear_options(state.sslCtx, SSL_OP_NO_COMPRESSION());
+                openssl_h_Compatibility.SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_NO_COMPRESSION());
             }
 
             // Disable TLS Session Tickets (RFC4507) to protect perfect 
forward secrecy
             if (sslHostConfig.getDisableSessionTickets()) {
-                SSL_CTX_set_options(state.sslCtx, SSL_OP_NO_TICKET());
+                openssl_h_Compatibility.SSL_CTX_set_options(state.sslCtx, 
SSL_OP_NO_TICKET());
             } else {
-                SSL_CTX_clear_options(state.sslCtx, SSL_OP_NO_TICKET());
+                openssl_h_Compatibility.SSL_CTX_clear_options(state.sslCtx, 
SSL_OP_NO_TICKET());
             }
 
             // List the ciphers that the client is permitted to negotiate
@@ -622,7 +623,7 @@ public class OpenSSLContext implements 
org.apache.tomcat.util.net.SSLContext {
                     log.error(sm.getString("openssl.errApplyConf"), e);
                 }
                 // Reconfigure the enabled protocols
-                long opts = SSL_CTX_get_options(state.sslCtx);
+                long opts = 
openssl_h_Compatibility.SSL_CTX_get_options(state.sslCtx);
                 List<String> enabled = new ArrayList<>();
                 // Seems like there is no way to explicitly disable SSLv2Hello
                 // in OpenSSL so it is always enabled
@@ -757,11 +758,11 @@ public class OpenSSLContext implements 
org.apache.tomcat.util.net.SSLContext {
             }
             MemorySegment ssl = X509_STORE_CTX_get_ex_data(x509_ctx, 
SSL_get_ex_data_X509_STORE_CTX_idx());
             MemorySegment /*STACK_OF(X509)*/ sk = 
X509_STORE_CTX_get0_untrusted(x509_ctx);
-            int len = OPENSSL_sk_num(sk);
+            int len = openssl_h_Compatibility.OPENSSL_sk_num(sk);
             byte[][] certificateChain = new byte[len][];
             try (var localArena = Arena.ofConfined()) {
                 for (int i = 0; i < len; i++) {
-                    MemorySegment/*(X509*)*/ x509 = OPENSSL_sk_value(sk, i);
+                    MemorySegment/*(X509*)*/ x509 = 
openssl_h_Compatibility.OPENSSL_sk_value(sk, i);
                     MemorySegment bufPointer = 
localArena.allocateFrom(ValueLayout.ADDRESS, MemorySegment.NULL);
                     int length = i2d_X509(x509, bufPointer);
                     if (length < 0) {
diff --git a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLEngine.java 
b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLEngine.java
index 5d3f5b0e8a..053d4747cf 100644
--- a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLEngine.java
+++ b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLEngine.java
@@ -64,6 +64,7 @@ import 
org.apache.tomcat.util.net.openssl.ciphers.OpenSSLCipherConfigurationPars
 import org.apache.tomcat.util.openssl.SSL_CTX_set_verify$callback;
 import org.apache.tomcat.util.openssl.SSL_set_info_callback$cb;
 import org.apache.tomcat.util.openssl.SSL_set_verify$callback;
+import org.apache.tomcat.util.openssl.openssl_h_Compatibility;
 import org.apache.tomcat.util.res.StringManager;
 
 /**
@@ -719,7 +720,7 @@ public final class OpenSSLEngine extends SSLEngine 
implements SSLUtil.ProtocolIn
         List<String> enabled = new ArrayList<>();
         // Seems like there is no way to explicitly disable SSLv2Hello in 
OpenSSL so it is always enabled
         enabled.add(Constants.SSL_PROTO_SSLv2Hello);
-        long opts = SSL_get_options(state.ssl);
+        long opts = openssl_h_Compatibility.SSL_get_options(state.ssl);
         if ((opts & SSL_OP_NO_TLSv1()) == 0) {
             enabled.add(Constants.SSL_PROTO_TLSv1);
         }
@@ -783,25 +784,25 @@ public final class OpenSSLEngine extends SSLEngine 
implements SSLUtil.ProtocolIn
             }
         }
         // Enable all and then disable what we not want
-        SSL_set_options(state.ssl, SSL_OP_ALL());
+        openssl_h_Compatibility.SSL_set_options(state.ssl, SSL_OP_ALL());
 
         if (!sslv2) {
-            SSL_set_options(state.ssl, SSL_OP_NO_SSLv2());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_SSLv2());
         }
         if (!sslv3) {
-            SSL_set_options(state.ssl, SSL_OP_NO_SSLv3());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_SSLv3());
         }
         if (!tlsv1) {
-            SSL_set_options(state.ssl, SSL_OP_NO_TLSv1());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_TLSv1());
         }
         if (!tlsv1_1) {
-            SSL_set_options(state.ssl, SSL_OP_NO_TLSv1_1());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_TLSv1_1());
         }
         if (!tlsv1_2) {
-            SSL_set_options(state.ssl, SSL_OP_NO_TLSv1_2());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_TLSv1_2());
         }
         if (!tlsv1_3) {
-            SSL_set_options(state.ssl, SSL_OP_NO_TLSv1_3());
+            openssl_h_Compatibility.SSL_set_options(state.ssl, 
SSL_OP_NO_TLSv1_3());
         }
     }
 
@@ -853,14 +854,14 @@ public final class OpenSSLEngine extends SSLEngine 
implements SSLUtil.ProtocolIn
 
     private byte[][] getPeerCertChain() {
         MemorySegment/*STACK_OF(X509)*/ sk = 
SSL_get_peer_cert_chain(state.ssl);
-        int len = OPENSSL_sk_num(sk);
+        int len = openssl_h_Compatibility.OPENSSL_sk_num(sk);
         if (len <= 0) {
             return null;
         }
         byte[][] certificateChain = new byte[len][];
         try (var localArena = Arena.ofConfined()) {
             for (int i = 0; i < len; i++) {
-                MemorySegment/*(X509*)*/ x509 = OPENSSL_sk_value(sk, i);
+                MemorySegment/*(X509*)*/ x509 = 
openssl_h_Compatibility.OPENSSL_sk_value(sk, i);
                 MemorySegment bufPointer = 
localArena.allocateFrom(ValueLayout.ADDRESS, MemorySegment.NULL);
                 int length = i2d_X509(x509, bufPointer);
                 if (length < 0) {
diff --git a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLLibrary.java 
b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLLibrary.java
index 8ca86e68e2..37f313e628 100644
--- a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLLibrary.java
+++ b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLLibrary.java
@@ -30,6 +30,7 @@ import org.apache.juli.logging.Log;
 import org.apache.juli.logging.LogFactory;
 import org.apache.tomcat.util.net.openssl.OpenSSLStatus;
 import 
org.apache.tomcat.util.net.openssl.ciphers.OpenSSLCipherConfigurationParser;
+import org.apache.tomcat.util.openssl.openssl_h_Compatibility;
 import org.apache.tomcat.util.res.StringManager;
 
 
@@ -421,7 +422,7 @@ public class OpenSSLLibrary {
             initLibrary();
             var sslCtx = SSL_CTX_new(TLS_server_method());
             try {
-                SSL_CTX_set_options(sslCtx, SSL_OP_ALL());
+                openssl_h_Compatibility.SSL_CTX_set_options(sslCtx, 
SSL_OP_ALL());
                 SSL_CTX_set_cipher_list(sslCtx, 
localArena.allocateFrom(ciphers));
                 var ssl = SSL_new(sslCtx);
                 SSL_set_accept_state(ssl);
@@ -447,13 +448,13 @@ public class OpenSSLLibrary {
 
     static String[] getCiphers(MemorySegment ssl) {
         MemorySegment sk = SSL_get_ciphers(ssl);
-        int len = OPENSSL_sk_num(sk);
+        int len = openssl_h_Compatibility.OPENSSL_sk_num(sk);
         if (len <= 0) {
             return null;
         }
         ArrayList<String> ciphers = new ArrayList<>(len);
         for (int i = 0; i < len; i++) {
-            MemorySegment cipher = OPENSSL_sk_value(sk, i);
+            MemorySegment cipher = 
openssl_h_Compatibility.OPENSSL_sk_value(sk, i);
             MemorySegment cipherName = SSL_CIPHER_get_name(cipher);
             ciphers.add(cipherName.getString(0));
         }
diff --git a/java/org/apache/tomcat/util/openssl/openssl_h.java 
b/java/org/apache/tomcat/util/openssl/openssl_h.java
index d3290392a9..c05333b953 100644
--- a/java/org/apache/tomcat/util/openssl/openssl_h.java
+++ b/java/org/apache/tomcat/util/openssl/openssl_h.java
@@ -32,6 +32,14 @@ import static java.lang.foreign.ValueLayout.*;
 @SuppressWarnings({"javadoc", "boxing"})
 public class openssl_h {
 
+    /*
+     * On Mac OS SymbolLookup.libraryLookup() appears to ignore 
java.library.path which means the LibreSSL
+     * library will be found which will then fail. Therefore, skip that lookup 
on Mac OS.
+     */
+    public static final boolean USE_SYSTEM_LOAD_LIBRARY = 
Boolean.getBoolean("org.apache.tomcat.util.openssl.USE_SYSTEM_LOAD_LIBRARY");
+    public static final String LIBRARY_NAME = 
System.getProperty("org.apache.tomcat.util.openssl.LIBRARY_NAME",
+            (JrePlatform.IS_MAC_OS) ? "ssl.48" : "ssl");
+
     openssl_h() {
         // Suppresses public default constructor, ensuring non-instantiability,
         // but allows generated subclasses in same package.
@@ -52,15 +60,11 @@ public class openssl_h {
     static final boolean TRACE_DOWNCALLS = 
Boolean.getBoolean("jextract.trace.downcalls");
     static final SymbolLookup SYMBOL_LOOKUP;
     static {
-        if (JrePlatform.IS_MAC_OS) {
-            /*
-             * On Mac OS SymbolLookup.libraryLookup() appears to ignore 
java.library.path which means the LibreSSL
-             * library will be found which will then fail. Therefore, skip 
that lookup on Mac OS.
-             */
-            System.loadLibrary("ssl");
+        if (USE_SYSTEM_LOAD_LIBRARY) {
+            System.loadLibrary(LIBRARY_NAME);
             SYMBOL_LOOKUP = 
SymbolLookup.loaderLookup().or(Linker.nativeLinker().defaultLookup());
         } else {
-            SYMBOL_LOOKUP = 
SymbolLookup.libraryLookup(System.mapLibraryName("ssl"), LIBRARY_ARENA)
+            SYMBOL_LOOKUP = 
SymbolLookup.libraryLookup(System.mapLibraryName(LIBRARY_NAME), LIBRARY_ARENA)
                     .or(SymbolLookup.loaderLookup())
                     .or(Linker.nativeLinker().defaultLookup());
         }
@@ -4262,6 +4266,40 @@ public class openssl_h {
         }
     }
 
+    private static MethodHandle SSL_ctrl$MH() {
+        class Holder {
+            static final FunctionDescriptor DESC = FunctionDescriptor.of(
+                openssl_h.C_LONG,
+                openssl_h.C_POINTER,
+                openssl_h.C_INT,
+                openssl_h.C_LONG,
+                openssl_h.C_POINTER
+            );
+
+            static final MethodHandle MH = 
Linker.nativeLinker().downcallHandle(
+                    openssl_h.findOrThrow("SSL_ctrl"),
+                    DESC);
+        }
+        return Holder.MH;
+    }
+
+    /**
+     * {@snippet lang=c :
+     * long SSL_ctrl(SSL *ssl, int cmd, long larg, void *parg)
+     * }
+     */
+    public static long SSL_ctrl(MemorySegment ssl, int cmd, long larg, 
MemorySegment parg) {
+        var mh$ = SSL_ctrl$MH();
+        try {
+            if (TRACE_DOWNCALLS) {
+                traceDowncall("SSL_ctrl", ssl, cmd, larg, parg);
+            }
+            return (long) mh$.invokeExact(ssl, cmd, larg, parg);
+        } catch (Throwable ex$) {
+           throw new AssertionError("should not reach here", ex$);
+        }
+    }
+
     private static MethodHandle SSL_get_version$MH() {
         class Holder {
             static final FunctionDescriptor DESC = FunctionDescriptor.of(
diff --git a/java/org/apache/tomcat/util/openssl/openssl_h_Compatibility.java 
b/java/org/apache/tomcat/util/openssl/openssl_h_Compatibility.java
index df2709ff6f..07513af8be 100644
--- a/java/org/apache/tomcat/util/openssl/openssl_h_Compatibility.java
+++ b/java/org/apache/tomcat/util/openssl/openssl_h_Compatibility.java
@@ -20,12 +20,18 @@ package org.apache.tomcat.util.openssl;
 import java.lang.invoke.MethodHandle;
 import java.lang.foreign.*;
 import static java.lang.foreign.ValueLayout.*;
+import static org.apache.tomcat.util.openssl.openssl_h.OpenSSL_version;
 
 /**
  * Methods used present in older OpenSSL versions but not in the current major 
version.
  */
 public class openssl_h_Compatibility {
 
+    public static final boolean LIBRESSL;
+    static {
+        LIBRESSL = OpenSSL_version(0).getString(0).contains("LibreSSL");
+    }
+
     // OpenSSL 1.1 FIPS_mode
     public static int FIPS_mode() {
         class Holder {
@@ -116,5 +122,100 @@ public class openssl_h_Compatibility {
         }
     }
 
+    // LibreSSL SSL_CTRL_OPTIONS
+    public static final int SSL_CTRL_OPTIONS = 32;
+
+    // LibreSSL SSL_CTX_get_options
+    public static long SSL_CTX_get_options(MemorySegment ctx) {
+        if (LIBRESSL) {
+            return openssl_h.SSL_CTX_ctrl(ctx, SSL_CTRL_OPTIONS, 0, 
MemorySegment.NULL);
+        } else {
+            return openssl_h.SSL_CTX_get_options(ctx);
+        }
+    }
+
+    // LibreSSL SSL_CTX_set_options
+    public static long SSL_CTX_set_options(MemorySegment ctx, long op) {
+        if (LIBRESSL) {
+            return openssl_h.SSL_CTX_ctrl(ctx, SSL_CTRL_OPTIONS, op, 
MemorySegment.NULL);
+        } else {
+            return openssl_h.SSL_CTX_set_options(ctx, op);
+        }
+    }
+
+    // LibreSSL SSL_get_options
+    public static long SSL_get_options(MemorySegment s) {
+        if (LIBRESSL) {
+            return openssl_h.SSL_ctrl(s, SSL_CTRL_OPTIONS, 0, 
MemorySegment.NULL);
+        } else {
+            return openssl_h.SSL_get_options(s);
+        }
+    }
+
+    // LibreSSL SSL_set_options
+    public static long SSL_set_options(MemorySegment s, long op) {
+        if (LIBRESSL) {
+            return openssl_h.SSL_ctrl(s, SSL_CTRL_OPTIONS, op, 
MemorySegment.NULL);
+        } else {
+            return openssl_h.SSL_set_options(s, op);
+        }
+    }
+
+    // LibreSSL SSL_CTRL_CLEAR_OPTIONS
+    public static final int SSL_CTRL_CLEAR_OPTIONS = 77;
+
+    // LibreSSL SSL_CTX_set_options
+    public static long SSL_CTX_clear_options(MemorySegment ctx, long op) {
+        if (LIBRESSL) {
+            return openssl_h.SSL_CTX_ctrl(ctx, SSL_CTRL_CLEAR_OPTIONS, op, 
MemorySegment.NULL);
+        } else {
+            return openssl_h.SSL_CTX_clear_options(ctx, op);
+        }
+    }
+
+    // LibreSSL OPENSSL_sk_num
+    public static int OPENSSL_sk_num(MemorySegment x0) {
+        if (LIBRESSL) {
+            class Holder {
+                static final String NAME = "sk_num";
+                static final FunctionDescriptor DESC = 
FunctionDescriptor.of(openssl_h.C_INT, openssl_h.C_POINTER);
+                static final MethodHandle MH = 
Linker.nativeLinker().downcallHandle(openssl_h.findOrThrow(NAME), DESC);
+            }
+            var mh$ = Holder.MH;
+            try {
+                if (openssl_h.TRACE_DOWNCALLS) {
+                    openssl_h.traceDowncall(Holder.NAME, x0);
+                }
+                return (int) mh$.invokeExact(x0);
+            } catch (Throwable ex$) {
+                throw new AssertionError("should not reach here", ex$);
+            }
+        } else {
+            return openssl_h.OPENSSL_sk_num(x0);
+        }
+    }
+
+    // LibreSSL OPENSSL_sk_value
+    public static MemorySegment OPENSSL_sk_value(MemorySegment x0, int x1) {
+        if (LIBRESSL) {
+            class Holder {
+                static final String NAME = "sk_value";
+                static final FunctionDescriptor DESC = 
FunctionDescriptor.of(openssl_h.C_POINTER, openssl_h.C_POINTER, 
openssl_h.C_INT);
+                static final MethodHandle MH = 
Linker.nativeLinker().downcallHandle(openssl_h.findOrThrow(NAME), DESC);
+            }
+            var mh$ = Holder.MH;
+            try {
+                if (openssl_h.TRACE_DOWNCALLS) {
+                    openssl_h.traceDowncall(Holder.NAME, x0, x1);
+                }
+                return (MemorySegment) mh$.invokeExact(x0, x1);
+            } catch (Throwable ex$) {
+                throw new AssertionError("should not reach here", ex$);
+            }
+        } else {
+            return openssl_h.OPENSSL_sk_value(x0, x1);
+        }
+    }
+
 }
 
diff --git a/test/org/apache/tomcat/util/net/openssl/TestOpenSSLConf.java 
b/test/org/apache/tomcat/util/net/openssl/TestOpenSSLConf.java
index cbf957d195..3bd32e6956 100644
--- a/test/org/apache/tomcat/util/net/openssl/TestOpenSSLConf.java
+++ b/test/org/apache/tomcat/util/net/openssl/TestOpenSSLConf.java
@@ -96,6 +96,7 @@ public class TestOpenSSLConf extends TomcatBaseTest {
         } else if 
("org.apache.tomcat.util.net.openssl.panama.OpenSSLImplementation".equals(sslImplementationName))
 {
             LifecycleListener listener = new OpenSSLLifecycleListener();
             Assume.assumeTrue(OpenSSLLifecycleListener.isAvailable());
+            
Assume.assumeFalse(Class.forName("org.apache.tomcat.util.openssl.openssl_h_Compatibility").getField("LIBRESSL").getBoolean(null));
             StandardServer server = (StandardServer) tomcat.getServer();
             server.addLifecycleListener(listener);
         }
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index 7f3c512cf1..abb8096aab 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -105,6 +105,22 @@
   issues do not "pop up" wrt. others).
 -->
 <section name="Tomcat 11.0.0-M23 (markt)" rtext="in development">
+  <subsection name="Coyote">
+    <changelog>
+      <update>
+        Add FFM compatibility methods for LibreSSL support. Renegotiation is
+        not supported at the moment. (remm)
+      </update>
+      <update>
+        Add <code>org.apache.tomcat.util.openssl.LIBRARY_NAME</code> (specifies
+        the name of the library to load) and
+        <code>org.apache.tomcat.util.openssl.USE_SYSTEM_LOAD_LIBRARY</code>
+        (set to <code>true</code> to use <code>System.loadLibrary</code> rather
+        than the FFM library loading code) to configure the OpenSSL library
+        loading using FFM. (remm)
+      </update>
+    </changelog>
+  </subsection>
 </section>
 <section name="Tomcat 11.0.0-M22 (markt)" rtext="release in progress">
   <subsection name="Catalina">
diff --git a/webapps/docs/config/systemprops.xml 
b/webapps/docs/config/systemprops.xml
index 0f5228c095..a720ca4d03 100644
--- a/webapps/docs/config/systemprops.xml
+++ b/webapps/docs/config/systemprops.xml
@@ -348,6 +348,19 @@
       <p>If not specified, the default value of <code>1000</code> will be 
used.</p>
     </property>
 
+    <property name="org.apache.tomcat.util.openssl.LIBRARY_NAME">
+      <p>Specify the library name of OpenSSL.</p>
+      <p>If not specified, the default value of <code>ssl</code> will be used,
+      except on MacOS where a dylib versioned name will be used, in the form of
+      <code>ssl.v</code> where v is a version number.</p>
+    </property>
+
+    <property name="org.apache.tomcat.util.openssl.USE_SYSTEM_LOAD_LIBRARY">
+      <p>Use <code>System.loadLibrary</code> to load OpenSSL rather than
+      the FFM library loading code.</p>
+      <p>If not specified, the default value of <code>false</code> will be 
used.</p>
+    </property>
+
     <property name="org.apache.catalina.startup. EXIT_ON_INIT_FAILURE">
       <p>If <code>true</code>, the server will exit if an exception happens
       during the server initialization phase. To support this feature, this


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org
For additional commands, e-mail: dev-h...@tomcat.apache.org

Reply via email to