SMACK-376 Allow supplying a custom SSLContext for encrypted connections.

The provided TrustManager / SSLContext implementation is very flexible,
but it does not allow to query the user about accepting possibly
invalid SSL certificates. By supplying a custom SSLContext with a
TrustManager implementing such a query mechanism it is possible to
implement this behaviour.

The patch adds ConnectionConfiguration.customSSLContext with appropriate
getter/setter methods and uses the custom context in XMPPConnection.

Signed-Off-By: Georg Lukas <georg@op-co.de>

git-svn-id: http://svn.igniterealtime.org/svn/repos/smack/trunk@13520 b35dd754-fafc-0310-a699-88a17e54d16e
This commit is contained in:
Florian Schmaus 2013-02-26 08:44:17 +00:00 committed by flow
parent c57843eeee
commit da1987a98b
2 changed files with 28 additions and 5 deletions

View File

@ -24,6 +24,7 @@ import org.jivesoftware.smack.proxy.ProxyInfo;
import org.jivesoftware.smack.util.DNSUtil;
import javax.net.SocketFactory;
import javax.net.ssl.SSLContext;
import javax.security.auth.callback.CallbackHandler;
import java.io.File;
@ -59,6 +60,7 @@ public class ConnectionConfiguration implements Cloneable {
private boolean selfSignedCertificateEnabled = false;
private boolean expiredCertificatesCheckEnabled = false;
private boolean notMatchingDomainCheckEnabled = false;
private SSLContext customSSLContext;
private boolean compressionEnabled = false;
@ -486,6 +488,25 @@ public class ConnectionConfiguration implements Cloneable {
this.notMatchingDomainCheckEnabled = notMatchingDomainCheckEnabled;
}
/**
* Gets the custom SSLContext for SSL sockets. This is null by default.
*
* @return the SSLContext previously set with setCustomSSLContext() or null.
*/
public SSLContext getCustomSSLContext() {
return this.customSSLContext;
}
/**
* Sets a custom SSLContext for creating SSL sockets. A custom Context causes all other
* SSL/TLS realted settings to be ignored.
*
* @param context the custom SSLContext for new sockets; null to reset default behavior.
*/
public void setCustomSSLContext(SSLContext context) {
this.customSSLContext = context;
}
/**
* Returns true if the connection is going to use stream compression. Stream compression
* will be requested after TLS was established (if TLS was enabled) and only if the server

View File

@ -763,14 +763,14 @@ public class XMPPConnection extends Connection {
* @throws Exception if an exception occurs.
*/
void proceedTLSReceived() throws Exception {
SSLContext context = SSLContext.getInstance("TLS");
SSLContext context = this.config.getCustomSSLContext();
KeyStore ks = null;
KeyManager[] kms = null;
PasswordCallback pcb = null;
if(config.getCallbackHandler() == null) {
ks = null;
} else {
} else if (context == null) {
//System.out.println("Keystore type: "+configuration.getKeystoreType());
if(config.getKeystoreType().equals("NONE")) {
ks = null;
@ -826,9 +826,11 @@ public class XMPPConnection extends Connection {
}
// Verify certificate presented by the server
context.init(kms,
new javax.net.ssl.TrustManager[]{new ServerTrustManager(getServiceName(), config)},
new java.security.SecureRandom());
if (context == null) {
context = SSLContext.getInstance("TLS");
context.init(kms, new javax.net.ssl.TrustManager[] { new ServerTrustManager(getServiceName(), config) },
new java.security.SecureRandom());
}
Socket plain = socket;
// Secure the plain connection
socket = context.getSocketFactory().createSocket(plain,