diff --git a/jetty-documentation/src/main/asciidoc/configuring/connectors/configuring-ssl.adoc b/jetty-documentation/src/main/asciidoc/configuring/connectors/configuring-ssl.adoc index 41408190c55..8fd729a0d4e 100644 --- a/jetty-documentation/src/main/asciidoc/configuring/connectors/configuring-ssl.adoc +++ b/jetty-documentation/src/main/asciidoc/configuring/connectors/configuring-ssl.adoc @@ -772,6 +772,12 @@ Both `setIncludeCipherSuites` and `setExcludeCipherSuites` can be fed by the exa If you have a need to adjust the Includes or Excludes, then this is best done with a custom XML that configures the `SslContextFactory` to suit your needs. +____ +[NOTE] +Jetty *does* allow users to enable weak/deprecated cipher suites (or even no cipher suites at all). +By default, if you have these suites enabled warning messages will appear in the server logs. +____ + To do this, first create a new `${jetty.base}/etc/tweak-ssl.xml` file (this can be any name, just avoid prefixing it with "jetty-"). [source, xml, subs="{sub-order}"] @@ -820,7 +826,7 @@ ____ ____ [TIP] -You can enable the `org.eclipse.jetty.util.ssl` named logger at DEBUG level to see what the list of selected Protocols and Cipher suites are at startup of Jetty. +You can enable the `org.eclipse.jetty.util.ssl` named logger at `DEBUG` level to see what the list of selected Protocols and Cipher suites are at startup of Jetty. ____ Additional Include / Exclude examples: diff --git a/jetty-server/src/main/config/etc/jetty-ssl-context.xml b/jetty-server/src/main/config/etc/jetty-ssl-context.xml index e5ed517dee2..22563921044 100644 --- a/jetty-server/src/main/config/etc/jetty-ssl-context.xml +++ b/jetty-server/src/main/config/etc/jetty-ssl-context.xml @@ -21,7 +21,7 @@ - + diff --git a/jetty-server/src/main/config/modules/https.mod b/jetty-server/src/main/config/modules/https.mod index 8136579de2c..b316a2edd41 100644 --- a/jetty-server/src/main/config/modules/https.mod +++ b/jetty-server/src/main/config/modules/https.mod @@ -1,4 +1,4 @@ -DO NOT EDIT - See: https://www.eclipse.org/jetty/documentation/current/startup-modules.html +# DO NOT EDIT - See: https://www.eclipse.org/jetty/documentation/current/startup-modules.html [description] Adds HTTPS protocol support to the TLS(SSL) Connector diff --git a/jetty-server/src/main/config/modules/ssl.mod b/jetty-server/src/main/config/modules/ssl.mod index 6f62ff583a3..11fd68ab136 100644 --- a/jetty-server/src/main/config/modules/ssl.mod +++ b/jetty-server/src/main/config/modules/ssl.mod @@ -59,6 +59,10 @@ basehome:modules/ssl/keystore|etc/keystore ## Note that OBF passwords are not secure, just protected from casual observation ## See http://www.eclipse.org/jetty/documentation/current/configuring-security-secure-passwords.html +## The Endpoint Identification Algorithm +## Same as javax.net.ssl.SSLParameters#setEndpointIdentificationAlgorithm(String) +#jetty.sslContext.endpointIdentificationAlgorithm=HTTPS + ## SSL JSSE Provider # jetty.sslContext.provider= diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/ssl/SslContextFactory.java b/jetty-util/src/main/java/org/eclipse/jetty/util/ssl/SslContextFactory.java index de50dd90667..eee32862b7b 100644 --- a/jetty-util/src/main/java/org/eclipse/jetty/util/ssl/SslContextFactory.java +++ b/jetty-util/src/main/java/org/eclipse/jetty/util/ssl/SslContextFactory.java @@ -113,6 +113,7 @@ public class SslContextFactory extends AbstractLifeCycle implements Dumpable }}; private static final Logger LOG = Log.getLogger(SslContextFactory.class); + private static final Logger LOG_CONFIG = LOG.getLogger("config"); public static final String DEFAULT_KEYMANAGERFACTORY_ALGORITHM = (Security.getProperty("ssl.KeyManagerFactory.algorithm") == null ? @@ -128,6 +129,24 @@ public class SslContextFactory extends AbstractLifeCycle implements Dumpable /** String name of keystore password property. */ public static final String PASSWORD_PROPERTY = "org.eclipse.jetty.ssl.password"; + /** Default Excluded Protocols List */ + private static final String[] DEFAULT_EXCLUDED_PROTOCOLS = {"SSL", "SSLv2", "SSLv2Hello", "SSLv3"}; + + /** Default Excluded Cipher Suite List */ + private static final String[] DEFAULT_EXCLUDED_CIPHER_SUITES = { + // Exclude weak / insecure ciphers + "^.*_(MD5|SHA|SHA1)$", + // Exclude ciphers that don't support forward secrecy + "^TLS_RSA_.*$", + // The following exclusions are present to cleanup known bad cipher + // suites that may be accidentally included via include patterns. + // The default enabled cipher list in Java will not include these + // (but they are available in the supported list). + "^SSL_.*$", + "^.*_NULL_.*$", + "^.*_anon_.*$" + }; + private final Set _excludeProtocols = new LinkedHashSet<>(); private final Set _includeProtocols = new LinkedHashSet<>(); private final Set _excludeCipherSuites = new LinkedHashSet<>(); @@ -210,19 +229,8 @@ public class SslContextFactory extends AbstractLifeCycle implements Dumpable private SslContextFactory(boolean trustAll, String keyStorePath) { setTrustAll(trustAll); - addExcludeProtocols("SSL", "SSLv2", "SSLv2Hello", "SSLv3"); - - // Exclude weak / insecure ciphers - setExcludeCipherSuites("^.*_(MD5|SHA|SHA1)$"); - // Exclude ciphers that don't support forward secrecy - addExcludeCipherSuites("^TLS_RSA_.*$"); - // The following exclusions are present to cleanup known bad cipher - // suites that may be accidentally included via include patterns. - // The default enabled cipher list in Java will not include these - // (but they are available in the supported list). - addExcludeCipherSuites("^SSL_.*$"); - addExcludeCipherSuites("^.*_NULL_.*$"); - addExcludeCipherSuites("^.*_anon_.*$"); + setExcludeProtocols(DEFAULT_EXCLUDED_PROTOCOLS); + setExcludeCipherSuites(DEFAULT_EXCLUDED_CIPHER_SUITES); if (keyStorePath != null) setKeyStorePath(keyStorePath); @@ -239,6 +247,38 @@ public class SslContextFactory extends AbstractLifeCycle implements Dumpable { load(); } + + secureConfigurationCheck(); + } + + protected void secureConfigurationCheck() + { + if (isTrustAll()) + LOG_CONFIG.warn("Trusting all certificates configured for {}",this); + if (getEndpointIdentificationAlgorithm()==null) + LOG_CONFIG.warn("No Client EndPointIdentificationAlgorithm configured for {}",this); + + SSLEngine engine = _factory._context.createSSLEngine(); + customize(engine); + SSLParameters supported = engine.getSSLParameters(); + + for (String protocol : supported.getProtocols()) + { + for (String excluded : DEFAULT_EXCLUDED_PROTOCOLS) + { + if (excluded.equals(protocol)) + LOG_CONFIG.warn("Protocol {} not excluded for {}", protocol, this); + } + } + + for (String suite : supported.getCipherSuites()) + { + for (String excludedSuiteRegex : DEFAULT_EXCLUDED_CIPHER_SUITES) + { + if (suite.matches(excludedSuiteRegex)) + LOG_CONFIG.warn("Weak cipher suite {} enabled for {}", suite, this); + } + } } private void load() throws Exception @@ -1064,8 +1104,9 @@ public class SslContextFactory extends AbstractLifeCycle implements Dumpable } /** - * When set to "HTTPS" hostname verification will be enabled - * + * When set to "HTTPS" hostname verification will be enabled. + * Deployments can be vulnerable to a man-in-the-middle attack if a EndpointIndentificationAlgorithm + * is not set. * @param endpointIdentificationAlgorithm Set the endpointIdentificationAlgorithm */ public void setEndpointIdentificationAlgorithm(String endpointIdentificationAlgorithm)