From 0d31b80cec97ff9e6d9135a219ffa4e993eb5242 Mon Sep 17 00:00:00 2001
From: Chris Ridd <chris.ridd@forgerock.com>
Date: Wed, 07 Sep 2016 12:49:11 +0000
Subject: [PATCH] OPENDJ-3221 Set better default TLS protocols which can also be overridden
---
opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java | 54 ++++++++++++++++++++++++---
opendj-server-legacy/src/main/java/org/opends/admin/ads/util/ConnectionWrapper.java | 11 ++++-
2 files changed, 57 insertions(+), 8 deletions(-)
diff --git a/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java b/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
index 0d05cf9..d5987df 100644
--- a/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
+++ b/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
@@ -21,10 +21,7 @@
import static com.forgerock.opendj.cli.CliMessages.*;
import static com.forgerock.opendj.cli.Utils.getHostNameForLdapUrl;
import static com.forgerock.opendj.cli.Utils.throwIfArgumentsConflict;
-import static org.forgerock.opendj.ldap.LDAPConnectionFactory.AUTHN_BIND_REQUEST;
-import static org.forgerock.opendj.ldap.LDAPConnectionFactory.CONNECT_TIMEOUT;
-import static org.forgerock.opendj.ldap.LDAPConnectionFactory.SSL_CONTEXT;
-import static org.forgerock.opendj.ldap.LDAPConnectionFactory.SSL_USE_STARTTLS;
+import static org.forgerock.opendj.ldap.LDAPConnectionFactory.*;
import static org.forgerock.util.time.Duration.*;
import static com.forgerock.opendj.cli.CommonArguments.*;
@@ -38,6 +35,9 @@
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
import java.util.concurrent.TimeUnit;
import javax.net.ssl.SSLContext;
@@ -345,6 +345,43 @@
}
/**
+ * Return a list of the available TLS protocols to use.
+ *
+ * <p>
+ * All protocols starting with "SSL" are removed. In particular the SSLv2Hello pseudo protocol is removed which will
+ * prevent connections to a server that doesn't have this configured.
+ * </p>
+ * <p>
+ * To override the defaults, set the <em>org.opends.ldaps.protocols</em> system property to a comma-separated list
+ * of desired protocols.
+ * </p>
+ *
+ * @return A list of valid protocol strings.
+ * @throws NoSuchAlgorithmException
+ * If an SSL context could not be created.
+ */
+ public static List<String> getDefaultProtocols() throws NoSuchAlgorithmException {
+ List<String> enabled = Arrays.asList(SSLContext.getDefault().createSSLEngine().getEnabledProtocols());
+ final String property = System.getProperty("org.opends.ldaps.protocols");
+ final List<String> defaults = new ArrayList<>();
+ if (property != null && property.length() != 0) {
+ for (String protocol : property.split(",")) {
+ if (enabled.contains(protocol)) {
+ defaults.add(protocol);
+ }
+ }
+ return defaults;
+ }
+ // exclude SSLv2Hello and SSLv3
+ for (String protocol : enabled) {
+ if (!protocol.startsWith("SSL")) {
+ defaults.add(protocol);
+ }
+ }
+ return defaults;
+ }
+
+ /**
* Constructs a connection factory for pre-authenticated connections. Checks if any conflicting arguments are
* present, build the connection with selected arguments and returns the connection factory. If the application is
* interactive, it will prompt the user for missing parameters.
@@ -427,8 +464,13 @@
Options options = Options.defaultOptions();
if (sslContext != null) {
- options.set(SSL_CONTEXT, sslContext)
- .set(SSL_USE_STARTTLS, useStartTLSArg.isPresent());
+ try {
+ options.set(SSL_CONTEXT, sslContext)
+ .set(SSL_USE_STARTTLS, useStartTLSArg.isPresent())
+ .set(SSL_ENABLED_PROTOCOLS, getDefaultProtocols());
+ } catch (NoSuchAlgorithmException e) {
+ throw new ArgumentException(ERR_LDAP_CONN_CANNOT_INITIALIZE_SSL.get(e.toString()), e);
+ }
}
options.set(CONNECT_TIMEOUT, duration(getConnectTimeout(), TimeUnit.MILLISECONDS));
if (usePreAuthentication) {
diff --git a/opendj-server-legacy/src/main/java/org/opends/admin/ads/util/ConnectionWrapper.java b/opendj-server-legacy/src/main/java/org/opends/admin/ads/util/ConnectionWrapper.java
index ce9447c..12a1de1 100644
--- a/opendj-server-legacy/src/main/java/org/opends/admin/ads/util/ConnectionWrapper.java
+++ b/opendj-server-legacy/src/main/java/org/opends/admin/ads/util/ConnectionWrapper.java
@@ -25,12 +25,14 @@
import java.io.Closeable;
import java.security.GeneralSecurityException;
+import java.security.NoSuchAlgorithmException;
import java.util.concurrent.TimeUnit;
import javax.net.ssl.KeyManager;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManager;
+import com.forgerock.opendj.cli.ConnectionFactoryProvider;
import org.forgerock.opendj.config.LDAPProfile;
import org.forgerock.opendj.ldap.Connection;
import org.forgerock.opendj.ldap.DN;
@@ -149,8 +151,13 @@
.set(CONNECT_TIMEOUT, duration(connectTimeout, TimeUnit.MILLISECONDS));
if (isLdaps || isStartTls)
{
- options.set(SSL_CONTEXT, getSSLContext(trustManager, keyManager))
- .set(SSL_USE_STARTTLS, isStartTls);
+ try {
+ options.set(SSL_CONTEXT, getSSLContext(trustManager, keyManager))
+ .set(SSL_USE_STARTTLS, isStartTls)
+ .set(SSL_ENABLED_PROTOCOLS, ConnectionFactoryProvider.getDefaultProtocols());
+ } catch (NoSuchAlgorithmException e) {
+ throw newLdapException(CLIENT_SIDE_PARAM_ERROR, "Unable to perform SSL initialization:" + e.getMessage());
+ }
}
SimpleBindRequest request = bindDn != null && bindPwd != null
? newSimpleBindRequest(bindDn.toString(), bindPwd.toCharArray())
--
Gitblit v1.10.0