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 84afdb004c Redo loading certificate chain 84afdb004c is described below commit 84afdb004cca8a475fa6f5505652e1fba3c693b5 Author: remm <r...@apache.org> AuthorDate: Tue Nov 14 15:31:44 2023 +0100 Redo loading certificate chain Use Java for loading the file, then a memory BIO to load the certificates one by one. --- .../util/net/openssl/panama/OpenSSLContext.java | 38 ++++++++++++++++++---- java/org/apache/tomcat/util/openssl/openssl_h.java | 8 +++++ res/openssl/openssl-tomcat.conf | 1 + webapps/docs/changelog.xml | 8 +++++ 4 files changed, 49 insertions(+), 6 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 aeda3b0232..1a70d72c63 100644 --- a/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java +++ b/java/org/apache/tomcat/util/net/openssl/panama/OpenSSLContext.java @@ -1114,7 +1114,7 @@ public class OpenSSLContext implements org.apache.tomcat.util.net.SSLContext { *# define ERR_SYSTEM_MASK ((unsigned int)INT_MAX) *# define ERR_REASON_MASK 0X7FFFFF */ - ((ERR_peek_last_error() & 0X7FFFFF) == PEM_R_NO_START_LINE())) { + ((ERR_peek_last_error() & ERR_REASON_MASK()) == PEM_R_NO_START_LINE())) { ERR_clear_error(); BIO_reset(certificateBIO); cert = d2i_X509_bio(certificateBIO, MemorySegment.NULL); @@ -1190,15 +1190,41 @@ public class OpenSSLContext implements org.apache.tomcat.util.net.SSLContext { EC_GROUP_free(ecparams); } } - // FIXME: Ideally these should be loaded in Java but still processed through OpenSSL // Set certificate chain file if (certificate.getCertificateChainFile() != null) { - var certificateChainFileNative = - localArena.allocateFrom(SSLHostConfig.adjustRelativePath(certificate.getCertificateChainFile())); + byte[] certificateChainBytes = null; + try (Resource resource = ConfigFileLoader.getSource().getResource(certificate.getCertificateChainFile())) { + certificateChainBytes = resource.getInputStream().readAllBytes(); + } catch (IOException e) { + log.error(sm.getString("openssl.errorLoadingCertificate", certificate.getCertificateChainFile()), e); + return false; + } // SSLContext.setCertificateChainFile(state.ctx, // SSLHostConfig.adjustRelativePath(certificate.getCertificateChainFile()), false); - if (SSL_CTX_use_certificate_chain_file(state.sslCtx, certificateChainFileNative) <= 0) { - log.error(sm.getString("openssl.errorLoadingCertificate", certificate.getCertificateChainFile())); + MemorySegment certificateChainBytesNative = localArena.allocateFrom(ValueLayout.JAVA_BYTE, certificateChainBytes); + MemorySegment certificateChainBIO = BIO_new(BIO_s_mem()); + try { + if (BIO_write(certificateChainBIO, certificateChainBytesNative, certificateChainBytes.length) <= 0) { + log.error(sm.getString("openssl.errorLoadingCertificate", "[0]:" + certificate.getCertificateChainFile())); + return false; + } + MemorySegment certChainEntry = + PEM_read_bio_X509_AUX(certificateChainBIO, MemorySegment.NULL, MemorySegment.NULL, MemorySegment.NULL); + while (!MemorySegment.NULL.equals(certChainEntry)) { + if (SSL_CTX_add0_chain_cert(state.sslCtx, certChainEntry) <= 0) { + log.error(sm.getString("openssl.errorLoadingCertificate", "[1]:" + certificate.getCertificateChainFile())); + } + certChainEntry = + PEM_read_bio_X509_AUX(certificateChainBIO, MemorySegment.NULL, MemorySegment.NULL, MemorySegment.NULL); + } + // EOF is accepted, otherwise log an error + if ((ERR_peek_last_error() & ERR_REASON_MASK()) == PEM_R_NO_START_LINE()) { + ERR_clear_error(); + } else { + log.error(sm.getString("openssl.errorLoadingCertificate", "[2]:" + certificate.getCertificateChainFile())); + } + } finally { + BIO_free(certificateChainBIO); } } // Set revocation diff --git a/java/org/apache/tomcat/util/openssl/openssl_h.java b/java/org/apache/tomcat/util/openssl/openssl_h.java index 0fde0bf82d..1115a7737d 100644 --- a/java/org/apache/tomcat/util/openssl/openssl_h.java +++ b/java/org/apache/tomcat/util/openssl/openssl_h.java @@ -594,6 +594,14 @@ public class openssl_h { public static int SSL_CTRL_SET_MAX_PROTO_VERSION() { return (int)124L; } + /** + * {@snippet : + * #define ERR_REASON_MASK 8388607 + * } + */ + public static int ERR_REASON_MASK() { + return (int)8388607L; + } /** * {@snippet : * #define OCSP_RESPONSE_STATUS_SUCCESSFUL 0 diff --git a/res/openssl/openssl-tomcat.conf b/res/openssl/openssl-tomcat.conf index 9aabb7914b..a44f2f7ec3 100644 --- a/res/openssl/openssl-tomcat.conf +++ b/res/openssl/openssl-tomcat.conf @@ -93,6 +93,7 @@ --include-function ERR_error_string # header: /usr/include/openssl/err.h --include-function ERR_get_error # header: /usr/include/openssl/err.h --include-function ERR_peek_last_error # header: /usr/include/openssl/err.h +--include-constant ERR_REASON_MASK # header: /usr/include/openssl/err.h #### Extracted from: /usr/include/openssl/evp.h diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml index 4c4b5cb0c2..f1df89f628 100644 --- a/webapps/docs/changelog.xml +++ b/webapps/docs/changelog.xml @@ -105,6 +105,14 @@ issues do not "pop up" wrt. others). --> <section name="Tomcat 11.0.0-M15 (markt)" rtext="in development"> + <subsection name="Coyote"> + <changelog> + <fix> + Use Java code to load certificate chain when using OpenSSL through + the FFM API. (remm) + </fix> + </changelog> + </subsection> <subsection name="Other"> <changelog> <update> --------------------------------------------------------------------- To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org For additional commands, e-mail: dev-h...@tomcat.apache.org