mirror of https://github.com/apache/cassandra
Remove hard-coded SSL cipher suites and protocols
patch by Stefan Podkowinski; reviewed by Robert Stupp for CASSANDRA-10508 backported in CASSANDRA-18575 by German Eichberger; reviewed by brandonwilliams
This commit is contained in:
parent
c91e2714b9
commit
e67fa69114
|
|
@ -1,4 +1,5 @@
|
||||||
3.0.30
|
3.0.30
|
||||||
|
* Backport CASSANDRA-10508: Remove hard-coded SSL cipher suites (CASSANDRA-18575)
|
||||||
* Suppress CVE-2023-2976 (CASSANDRA-18562)
|
* Suppress CVE-2023-2976 (CASSANDRA-18562)
|
||||||
* Remove dh_python use in Debian packaging (CASSANDRA-18558)
|
* Remove dh_python use in Debian packaging (CASSANDRA-18558)
|
||||||
* Pass down all contact points to driver for cassandra-stress (CASSANDRA-18025)
|
* Pass down all contact points to driver for cassandra-stress (CASSANDRA-18025)
|
||||||
|
|
|
||||||
|
|
@ -909,10 +909,14 @@ request_scheduler: org.apache.cassandra.scheduler.NoScheduler
|
||||||
# request_scheduler_id: keyspace
|
# request_scheduler_id: keyspace
|
||||||
|
|
||||||
# Enable or disable inter-node encryption
|
# Enable or disable inter-node encryption
|
||||||
# Default settings are TLS v1, RSA 1024-bit keys (it is imperative that
|
# JVM defaults for supported SSL socket protocols and cipher suites can
|
||||||
# users generate their own keys) TLS_RSA_WITH_AES_128_CBC_SHA as the cipher
|
# be replaced using custom encryption options. This is not recommended
|
||||||
# suite for authentication, key exchange and encryption of the actual data transfers.
|
# unless you have policies in place that dictate certain settings, or
|
||||||
# Use the DHE/ECDHE ciphers if running in FIPS 140 compliant mode.
|
# need to disable vulnerable ciphers or protocols in case the JVM cannot
|
||||||
|
# be updated.
|
||||||
|
# FIPS compliant settings can be configured at JVM level and should not
|
||||||
|
# involve changing encryption settings here:
|
||||||
|
# https://docs.oracle.com/javase/8/docs/technotes/guides/security/jsse/FIPS.html
|
||||||
# NOTE: No custom encryption options are enabled at the moment
|
# NOTE: No custom encryption options are enabled at the moment
|
||||||
# The available internode options are : all, none, dc, rack
|
# The available internode options are : all, none, dc, rack
|
||||||
#
|
#
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,8 @@
|
||||||
*/
|
*/
|
||||||
package org.apache.cassandra.config;
|
package org.apache.cassandra.config;
|
||||||
|
|
||||||
|
import javax.net.ssl.SSLSocketFactory;
|
||||||
|
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
|
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
|
|
@ -33,11 +35,7 @@ public abstract class EncryptionOptions
|
||||||
public String keystore_password = "cassandra";
|
public String keystore_password = "cassandra";
|
||||||
public String truststore = "conf/.truststore";
|
public String truststore = "conf/.truststore";
|
||||||
public String truststore_password = "cassandra";
|
public String truststore_password = "cassandra";
|
||||||
public String[] cipher_suites = {
|
public String[] cipher_suites = ((SSLSocketFactory)SSLSocketFactory.getDefault()).getDefaultCipherSuites();
|
||||||
"TLS_RSA_WITH_AES_128_CBC_SHA", "TLS_RSA_WITH_AES_256_CBC_SHA",
|
|
||||||
"TLS_DHE_RSA_WITH_AES_128_CBC_SHA", "TLS_DHE_RSA_WITH_AES_256_CBC_SHA",
|
|
||||||
"TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA", "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA"
|
|
||||||
};
|
|
||||||
public String protocol = "TLS";
|
public String protocol = "TLS";
|
||||||
public String algorithm = "SunX509";
|
public String algorithm = "SunX509";
|
||||||
public String store_type = "JKS";
|
public String store_type = "JKS";
|
||||||
|
|
@ -55,7 +53,6 @@ public abstract class EncryptionOptions
|
||||||
{
|
{
|
||||||
all, none, dc, rack
|
all, none, dc, rack
|
||||||
}
|
}
|
||||||
|
|
||||||
public InternodeEncryption internode_encryption = InternodeEncryption.none;
|
public InternodeEncryption internode_encryption = InternodeEncryption.none;
|
||||||
|
|
||||||
public boolean shouldEncrypt(InetAddress endpoint)
|
public boolean shouldEncrypt(InetAddress endpoint)
|
||||||
|
|
|
||||||
|
|
@ -53,28 +53,18 @@ import com.google.common.collect.Sets;
|
||||||
public final class SSLFactory
|
public final class SSLFactory
|
||||||
{
|
{
|
||||||
private static final Logger logger = LoggerFactory.getLogger(SSLFactory.class);
|
private static final Logger logger = LoggerFactory.getLogger(SSLFactory.class);
|
||||||
public static final String[] ACCEPTED_PROTOCOLS = new String[] {"SSLv2Hello", "TLSv1", "TLSv1.1", "TLSv1.2"};
|
|
||||||
private static boolean checkedExpiry = false;
|
private static boolean checkedExpiry = false;
|
||||||
|
|
||||||
public static SSLServerSocket getServerSocket(EncryptionOptions options, InetAddress address, int port) throws IOException
|
public static SSLServerSocket getServerSocket(EncryptionOptions options, InetAddress address, int port) throws IOException
|
||||||
{
|
{
|
||||||
SSLContext ctx = createSSLContext(options, true);
|
SSLContext ctx = createSSLContext(options, true);
|
||||||
SSLServerSocket serverSocket = (SSLServerSocket) ctx.getServerSocketFactory().createServerSocket();
|
SSLServerSocket serverSocket = (SSLServerSocket)ctx.getServerSocketFactory().createServerSocket();
|
||||||
try
|
serverSocket.setReuseAddress(true);
|
||||||
{
|
String[] suites = filterCipherSuites(serverSocket.getSupportedCipherSuites(), options.cipher_suites);
|
||||||
serverSocket.setReuseAddress(true);
|
serverSocket.setEnabledCipherSuites(suites);
|
||||||
String[] suites = filterCipherSuites(serverSocket.getSupportedCipherSuites(), options.cipher_suites);
|
serverSocket.setNeedClientAuth(options.require_client_auth);
|
||||||
serverSocket.setEnabledCipherSuites(suites);
|
serverSocket.bind(new InetSocketAddress(address, port), 500);
|
||||||
serverSocket.setNeedClientAuth(options.require_client_auth);
|
return serverSocket;
|
||||||
serverSocket.setEnabledProtocols(ACCEPTED_PROTOCOLS);
|
|
||||||
serverSocket.bind(new InetSocketAddress(address, port), 500);
|
|
||||||
return serverSocket;
|
|
||||||
}
|
|
||||||
catch (IllegalArgumentException | SecurityException | IOException e)
|
|
||||||
{
|
|
||||||
serverSocket.close();
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Create a socket and connect */
|
/** Create a socket and connect */
|
||||||
|
|
@ -82,18 +72,9 @@ public final class SSLFactory
|
||||||
{
|
{
|
||||||
SSLContext ctx = createSSLContext(options, true);
|
SSLContext ctx = createSSLContext(options, true);
|
||||||
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket(address, port, localAddress, localPort);
|
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket(address, port, localAddress, localPort);
|
||||||
try
|
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
||||||
{
|
socket.setEnabledCipherSuites(suites);
|
||||||
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
return socket;
|
||||||
socket.setEnabledCipherSuites(suites);
|
|
||||||
socket.setEnabledProtocols(ACCEPTED_PROTOCOLS);
|
|
||||||
return socket;
|
|
||||||
}
|
|
||||||
catch (IllegalArgumentException e)
|
|
||||||
{
|
|
||||||
socket.close();
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Create a socket and connect, using any local address */
|
/** Create a socket and connect, using any local address */
|
||||||
|
|
@ -101,18 +82,9 @@ public final class SSLFactory
|
||||||
{
|
{
|
||||||
SSLContext ctx = createSSLContext(options, true);
|
SSLContext ctx = createSSLContext(options, true);
|
||||||
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket(address, port);
|
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket(address, port);
|
||||||
try
|
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
||||||
{
|
socket.setEnabledCipherSuites(suites);
|
||||||
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
return socket;
|
||||||
socket.setEnabledCipherSuites(suites);
|
|
||||||
socket.setEnabledProtocols(ACCEPTED_PROTOCOLS);
|
|
||||||
return socket;
|
|
||||||
}
|
|
||||||
catch (IllegalArgumentException e)
|
|
||||||
{
|
|
||||||
socket.close();
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Just create a socket */
|
/** Just create a socket */
|
||||||
|
|
@ -120,18 +92,9 @@ public final class SSLFactory
|
||||||
{
|
{
|
||||||
SSLContext ctx = createSSLContext(options, true);
|
SSLContext ctx = createSSLContext(options, true);
|
||||||
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket();
|
SSLSocket socket = (SSLSocket) ctx.getSocketFactory().createSocket();
|
||||||
try
|
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
||||||
{
|
socket.setEnabledCipherSuites(suites);
|
||||||
String[] suites = filterCipherSuites(socket.getSupportedCipherSuites(), options.cipher_suites);
|
return socket;
|
||||||
socket.setEnabledCipherSuites(suites);
|
|
||||||
socket.setEnabledProtocols(ACCEPTED_PROTOCOLS);
|
|
||||||
return socket;
|
|
||||||
}
|
|
||||||
catch (IllegalArgumentException e)
|
|
||||||
{
|
|
||||||
socket.close();
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings("resource")
|
@SuppressWarnings("resource")
|
||||||
|
|
|
||||||
|
|
@ -257,8 +257,7 @@ public class CustomTThreadPoolServer extends TServer
|
||||||
SSLServerSocket sslServerSocket = (SSLServerSocket) sslServer.getServerSocket();
|
SSLServerSocket sslServerSocket = (SSLServerSocket) sslServer.getServerSocket();
|
||||||
String[] suites = SSLFactory.filterCipherSuites(sslServerSocket.getSupportedCipherSuites(), clientEnc.cipher_suites);
|
String[] suites = SSLFactory.filterCipherSuites(sslServerSocket.getSupportedCipherSuites(), clientEnc.cipher_suites);
|
||||||
sslServerSocket.setEnabledCipherSuites(suites);
|
sslServerSocket.setEnabledCipherSuites(suites);
|
||||||
sslServerSocket.setEnabledProtocols(SSLFactory.ACCEPTED_PROTOCOLS);
|
serverTransport = new TCustomServerSocket(sslServerSocket, args.keepAlive, args.sendBufferSize, args.recvBufferSize);
|
||||||
serverTransport = new TCustomServerSocket(sslServer.getServerSocket(), args.keepAlive, args.sendBufferSize, args.recvBufferSize);
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -418,7 +418,6 @@ public class Server implements CassandraDaemon.Server
|
||||||
String[] suites = SSLFactory.filterCipherSuites(sslEngine.getSupportedCipherSuites(), encryptionOptions.cipher_suites);
|
String[] suites = SSLFactory.filterCipherSuites(sslEngine.getSupportedCipherSuites(), encryptionOptions.cipher_suites);
|
||||||
sslEngine.setEnabledCipherSuites(suites);
|
sslEngine.setEnabledCipherSuites(suites);
|
||||||
sslEngine.setNeedClientAuth(encryptionOptions.require_client_auth);
|
sslEngine.setNeedClientAuth(encryptionOptions.require_client_auth);
|
||||||
sslEngine.setEnabledProtocols(SSLFactory.ACCEPTED_PROTOCOLS);
|
|
||||||
return new SslHandler(sslEngine);
|
return new SslHandler(sslEngine);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -308,7 +308,6 @@ public class SimpleClient implements Closeable
|
||||||
sslEngine.setUseClientMode(true);
|
sslEngine.setUseClientMode(true);
|
||||||
String[] suites = SSLFactory.filterCipherSuites(sslEngine.getSupportedCipherSuites(), encryptionOptions.cipher_suites);
|
String[] suites = SSLFactory.filterCipherSuites(sslEngine.getSupportedCipherSuites(), encryptionOptions.cipher_suites);
|
||||||
sslEngine.setEnabledCipherSuites(suites);
|
sslEngine.setEnabledCipherSuites(suites);
|
||||||
sslEngine.setEnabledProtocols(SSLFactory.ACCEPTED_PROTOCOLS);
|
|
||||||
channel.pipeline().addFirst("ssl", new SslHandler(sslEngine));
|
channel.pipeline().addFirst("ssl", new SslHandler(sslEngine));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue